```ts
function regionTotals(grid: number[][], queries: number[][]): number[] {
  if (!Array.isArray(grid) || grid.length === 0) {
    throw new Error("grid must be a non-empty list of rows");
  }
  const width = Array.isArray(grid[0]) ? grid[0].length : 0;
  if (width === 0) {
    throw new Error("rows must be non-empty lists");
  }
  for (const row of grid) {
    if (!Array.isArray(row) || row.length !== width) {
      throw new Error("rows must all share one length");
    }
    for (const cell of row) {
      if (!Number.isInteger(cell)) {
        throw new Error("cells must be integers");
      }
    }
  }

  const prefixSum = grid.map((row, i) => row.map((cell, j) => {
    if (i === 0 && j === 0) return cell;
    if (i === 0) return cell + prefixSum[i][j - 1];
    if (j === 0) return cell + prefixSum[i - 1][j];
    return cell + prefixSum[i - 1][j - 1];
  }));

  const result: number[] = [];
  for (const query of queries) {
    const [top, left, bottom, right] = query;
    if (top >= bottom || left >= right) {
      throw new Error("query must have top < bottom and left < right");
    }
    if (top < 0 || left < 0 || bottom >= grid.length || right >= width) {
      throw new Error("query must be within the grid bounds");
    }
    const sum = prefixSum[bottom - 1][right - 1] -
                 (top > 0 ? prefixSum[top - 1][right - 1] : 0) -
                 (left > 0 ? prefixSum[bottom - 1][left - 1] : 0) +
                 (top > 0 && left > 0 ? prefixSum[top - 1][left - 1] : 0);
    result.push(sum);
  }

  return result;
}
```