* Add an error-location display to the error message under construction. * * The cursor location is measured in logical characters; the query string * is presumed to be in the specified encoding. */
| 1351 | * is presumed to be in the specified encoding. |
| 1352 | */ |
| 1353 | static void |
| 1354 | reportErrorPosition(PQExpBuffer msg, const char *query, int loc, int encoding) |
| 1355 | { |
| 1356 | #define DISPLAY_SIZE 60 /* screen width limit, in screen cols */ |
| 1357 | #define MIN_RIGHT_CUT 10 /* try to keep this far away from EOL */ |
| 1358 | |
| 1359 | char *wquery; |
| 1360 | int slen, |
| 1361 | cno, |
| 1362 | i, |
| 1363 | *qidx, |
| 1364 | *scridx, |
| 1365 | qoffset, |
| 1366 | scroffset, |
| 1367 | ibeg, |
| 1368 | iend, |
| 1369 | loc_line; |
| 1370 | bool mb_encoding, |
| 1371 | beg_trunc, |
| 1372 | end_trunc; |
| 1373 | |
| 1374 | /* Convert loc from 1-based to 0-based; no-op if out of range */ |
| 1375 | loc--; |
| 1376 | if (loc < 0) |
| 1377 | return; |
| 1378 | |
| 1379 | /* Need a writable copy of the query */ |
| 1380 | wquery = strdup(query); |
| 1381 | if (wquery == NULL) |
| 1382 | return; /* fail silently if out of memory */ |
| 1383 | |
| 1384 | /* |
| 1385 | * Each character might occupy multiple physical bytes in the string, and |
| 1386 | * in some Far Eastern character sets it might take more than one screen |
| 1387 | * column as well. We compute the starting byte offset and starting |
| 1388 | * screen column of each logical character, and store these in qidx[] and |
| 1389 | * scridx[] respectively. |
| 1390 | */ |
| 1391 | |
| 1392 | /* we need a safe allocation size... */ |
| 1393 | slen = strlen(wquery) + 1; |
| 1394 | |
| 1395 | qidx = (int *) malloc(slen * sizeof(int)); |
| 1396 | if (qidx == NULL) |
| 1397 | { |
| 1398 | free(wquery); |
| 1399 | return; |
| 1400 | } |
| 1401 | scridx = (int *) malloc(slen * sizeof(int)); |
| 1402 | if (scridx == NULL) |
| 1403 | { |
| 1404 | free(qidx); |
| 1405 | free(wquery); |
| 1406 | return; |
| 1407 | } |
| 1408 | |
| 1409 | /* We can optimize a bit if it's a single-byte encoding */ |
| 1410 | mb_encoding = (pg_encoding_max_length(encoding) != 1); |
no test coverage detected