Según el manual, sobre el resultado de la función sqlsrv_query:
Returns a statement resource on success and FALSE if an error occurred.
O sea, que devuelve un recurso válido o false. En tu código no compruebas si la consulta tuvo éxito (mala costumbre) y automáticamente llamas a sqlsrv_num_rows() pasándole como argumento en vez de un recurso válido, un false, pues muy probablemente la consulta no tuvo éxito o tuvo algún error.
Primero deberías comprobar si la consulta tuvo éxito:
$results = sqlsrv_query($conn, $query, array(), array("Scrollable"=>"buffered"));if($results === false){echo "Error en la consulta: $query";}else{ // tu código if (sqlsrv_num_rows($results) == 0) { //checa si hay resultados $hay = 0; } else { $hay = 1; $headers = array_keys($results->fetch_assoc()); }}
Y luego qué es lo que falló, la sintaxis de la consulta o algún otro factor.