PostgreSQL Source Code: src/interfaces/ecpg/ecpglib/execute.c Source File (original) (raw)

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16#define POSTGRES_ECPG_INTERNAL

18

19#include <math.h>

20

21#include "catalog/pg_type_d.h"

34

35

36

37

38

39static char *

41{

42 char *res;

43 size_t length;

44 size_t escaped_len;

45 size_t buffer_len;

46

47

48

49

50

51 if (!quote)

52 return arg;

53 else

54 {

55 length = strlen(arg);

56 buffer_len = 2 * length + 1;

57 res = ecpg_alloc(buffer_len + 3, lineno);

58 if (!res)

59 return res;

61 if (length == escaped_len)

62 {

63 res[0] = res[escaped_len + 1] = '\'';

64 res[escaped_len + 2] = '\0';

65 }

66 else

67 {

68

69

70

71

72 memmove(res + 2, res + 1, escaped_len);

74 res[1] = res[escaped_len + 2] = '\'';

75 res[escaped_len + 3] = '\0';

76 }

78 return res;

79 }

80}

81

82static void

84{

86

87 while (var)

88 {

89 var_next = var->next;

91 var = var_next;

92 }

93}

94

95static void

97{

98 if (stmt == NULL)

99 return;

104#ifndef HAVE_USELOCALE

106#endif

108}

109

110static int

112{

113 bool string = false;

114 int p = pos;

115

116 for (; text[p] != '\0'; p++)

117 {

118 if (string && !std_strings && text[p] == '\\')

119 p++;

120 else if (text[p] == '\'')

121 string = string ? false : true;

122 else if (!string)

123 {

124 if (text[p] == '$' && isdigit((unsigned char) text[p + 1]))

125 {

126

127 int i;

128

129 for (i = p + 1; isdigit((unsigned char) text[i]); i++)

130 ;

131 if (!isalpha((unsigned char) text[i]) &&

132 isascii((unsigned char) text[i]) && text[i] != '_')

133

134 return p;

135 }

137 {

138

139 return p;

140 }

141 }

142 }

143

144 return -1;

145}

146

147static bool

149{

152

153 if (new_entry == NULL)

154 return false;

155

156 new_entry->oid = oid;

158 new_entry->next = *cache;

159 *cache = new_entry;

160 return true;

161}

162

165{

166 char *array_query;

170

171 if ((stmt->connection->cache_head) == NULL)

172 {

173

174

175

176

177#define not_an_array_in_ecpg ECPG_ARRAY_NONE

178

179

258 }

259

260 for (cache_entry = (stmt->connection->cache_head); cache_entry != NULL; cache_entry = cache_entry->next)

261 {

262 if (cache_entry->oid == type)

263 return cache_entry->isarray;

264 }

265

266 array_query = ecpg_alloc(strlen("select typlen from pg_type where oid= and typelem<>0") + 11, stmt->lineno);

267 if (array_query == NULL)

269

270 sprintf(array_query, "select typlen from pg_type where oid=%d and typelem<>0", type);

271 query = PQexec(stmt->connection->connection, array_query);

276 {

279 else

280 {

284 {

285

286

287

289 }

290 }

292 }

293 else

295

299}

300

301

302bool

305{

307 int act_tuple,

309 bool status = true;

310

312 {

314 return false;

315 }

316

318 {

319

320

321

323 {

324 ecpg_log("ecpg_store_result on line %d: incorrect number of matches; %d don't fit into array of %ld\n",

327 return false;

328 }

329 }

330 else

331 {

332

333

334

336 {

338 return false;

339 }

340 }

341

342

343

344

346 {

347 int len = 0;

348

349 if (PQfformat(results, act_field))

350 {

351 switch (var->type)

352 {

357 {

358

359 for (act_tuple = 0; act_tuple < ntuples; act_tuple++)

360 len += strlen(PQgetvalue(results, act_tuple, act_field)) + 1;

361 len *= var->offset;

362 len += (ntuples + 1) * sizeof(char *);

363 }

364 else

365 {

367

368 for (act_tuple = 0; act_tuple < ntuples; act_tuple++)

369 {

370 int slen = strlen(PQgetvalue(results, act_tuple, act_field)) + 1;

371

374 }

377 }

378 break;

381 break;

382 default:

384 break;

385 }

386 }

387 else

388 {

389 for (act_tuple = 0; act_tuple < ntuples; act_tuple++)

391 }

392

393 ecpg_log("ecpg_store_result on line %d: allocating memory for %d tuples\n", stmt->lineno, ntuples);

396 return false;

398 }

399

400

402 {

404

407 return false;

409 }

410

411

414 {

415

416

417

418 char **current_string = (char **) var->value;

419

420

421 char *current_data_location = (char *) &current_string[ntuples + 1];

422

423 for (act_tuple = 0; act_tuple < ntuples && status; act_tuple++)

424 {

425 int len = strlen(PQgetvalue(results, act_tuple, act_field)) + 1;

426

428 var->type, var->ind_type, current_data_location,

430 status = false;

431 else

432 {

433 *current_string = current_data_location;

434 current_data_location += len;

435 current_string++;

436 }

437 }

438

439

440 *current_string = NULL;

441 }

442 else

443 {

444 for (act_tuple = 0; act_tuple < ntuples && status; act_tuple++)

445 {

449 status = false;

450 }

451 }

452 return status;

453}

454

455static void

457{

458 if (isnan(value))

459 sprintf(ptr, "%s%s", "NaN", delim);

460 else if (isinf(value))

461 {

463 sprintf(ptr, "%s%s", "-Infinity", delim);

464 else

465 sprintf(ptr, "%s%s", "Infinity", delim);

466 }

467 else

469}

470

471static void

473{

474 if (isnan(value))

475 sprintf(ptr, "%s%s", "NaN", delim);

476 else if (isinf(value))

477 {

479 sprintf(ptr, "%s%s", "-Infinity", delim);

480 else

481 sprintf(ptr, "%s%s", "Infinity", delim);

482 }

483 else

485}

486

487static char *

489{

490 char *to_data;

491 int to_len = ecpg_hex_enc_len(from_len) + 4 + 1;

492

493

494 to_data = ecpg_alloc(to_len, lineno);

495 if (!to_data)

496 return NULL;

497

498 strcpy(to_data, "'\\x");

501

502 return to_data;

503}

504

505bool

507 char **tobeinserted_p, bool quote)

508{

509 char *mallocedval = NULL;

510 char *newcopy = NULL;

511

512

513

514

515

516

517

518

519

520

521

522

523 *tobeinserted_p = "";

524

525

527 {

530 if (*(short *) var->ind_value < 0)

531 *tobeinserted_p = NULL;

532 break;

536 *tobeinserted_p = NULL;

537 break;

540 if (*(long *) var->ind_value < 0L)

541 *tobeinserted_p = NULL;

542 break;

545 if (*(long long int *) var->ind_value < (long long) 0)

546 *tobeinserted_p = NULL;

547 break;

550 {

552 *tobeinserted_p = NULL;

553 }

554 break;

555 default:

556 break;

557 }

558 if (*tobeinserted_p != NULL)

559 {

561

562 switch (var->type)

563 {

565

567 if (!(mallocedval = ecpg_alloc(asize * 20, lineno)))

568 return false;

569

570 if (asize > 1)

571 {

572 strcpy(mallocedval, "{");

573

575 sprintf(mallocedval + strlen(mallocedval), "%hd,", ((short *) var->value)[element]);

576

577 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

578 }

579 else

580 sprintf(mallocedval, "%hd", *((short *) var->value));

581

582 *tobeinserted_p = mallocedval;

583 break;

584

586 if (!(mallocedval = ecpg_alloc(asize * 20, lineno)))

587 return false;

588

589 if (asize > 1)

590 {

591 strcpy(mallocedval, "{");

592

594 sprintf(mallocedval + strlen(mallocedval), "%d,", ((int *) var->value)[element]);

595

596 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

597 }

598 else

599 sprintf(mallocedval, "%d", *((int *) var->value));

600

601 *tobeinserted_p = mallocedval;

602 break;

603

605 if (!(mallocedval = ecpg_alloc(asize * 20, lineno)))

606 return false;

607

608 if (asize > 1)

609 {

610 strcpy(mallocedval, "{");

611

613 sprintf(mallocedval + strlen(mallocedval), "%hu,", ((unsigned short *) var->value)[element]);

614

615 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

616 }

617 else

618 sprintf(mallocedval, "%hu", *((unsigned short *) var->value));

619

620 *tobeinserted_p = mallocedval;

621 break;

622

624 if (!(mallocedval = ecpg_alloc(asize * 20, lineno)))

625 return false;

626

627 if (asize > 1)

628 {

629 strcpy(mallocedval, "{");

630

632 sprintf(mallocedval + strlen(mallocedval), "%u,", ((unsigned int *) var->value)[element]);

633

634 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

635 }

636 else

637 sprintf(mallocedval, "%u", *((unsigned int *) var->value));

638

639 *tobeinserted_p = mallocedval;

640 break;

641

643 if (!(mallocedval = ecpg_alloc(asize * 20, lineno)))

644 return false;

645

646 if (asize > 1)

647 {

648 strcpy(mallocedval, "{");

649

651 sprintf(mallocedval + strlen(mallocedval), "%ld,", ((long *) var->value)[element]);

652

653 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

654 }

655 else

656 sprintf(mallocedval, "%ld", *((long *) var->value));

657

658 *tobeinserted_p = mallocedval;

659 break;

660

662 if (!(mallocedval = ecpg_alloc(asize * 20, lineno)))

663 return false;

664

665 if (asize > 1)

666 {

667 strcpy(mallocedval, "{");

668

670 sprintf(mallocedval + strlen(mallocedval), "%lu,", ((unsigned long *) var->value)[element]);

671

672 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

673 }

674 else

675 sprintf(mallocedval, "%lu", *((unsigned long *) var->value));

676

677 *tobeinserted_p = mallocedval;

678 break;

679

681 if (!(mallocedval = ecpg_alloc(asize * 30, lineno)))

682 return false;

683

684 if (asize > 1)

685 {

686 strcpy(mallocedval, "{");

687

689 sprintf(mallocedval + strlen(mallocedval), "%lld,", ((long long int *) var->value)[element]);

690

691 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

692 }

693 else

694 sprintf(mallocedval, "%lld", *((long long int *) var->value));

695

696 *tobeinserted_p = mallocedval;

697 break;

698

700 if (!(mallocedval = ecpg_alloc(asize * 30, lineno)))

701 return false;

702

703 if (asize > 1)

704 {

705 strcpy(mallocedval, "{");

706

708 sprintf(mallocedval + strlen(mallocedval), "%llu,", ((unsigned long long int *) var->value)[element]);

709

710 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

711 }

712 else

713 sprintf(mallocedval, "%llu", *((unsigned long long int *) var->value));

714

715 *tobeinserted_p = mallocedval;

716 break;

717

719 if (!(mallocedval = ecpg_alloc(asize * 25, lineno)))

720 return false;

721

722 if (asize > 1)

723 {

724 strcpy(mallocedval, "{");

725

728

729 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

730 }

731 else

733

734 *tobeinserted_p = mallocedval;

735 break;

736

738 if (!(mallocedval = ecpg_alloc(asize * 25, lineno)))

739 return false;

740

741 if (asize > 1)

742 {

743 strcpy(mallocedval, "{");

744

747

748 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

749 }

750 else

752

753 *tobeinserted_p = mallocedval;

754 break;

755

757 if (!(mallocedval = ecpg_alloc(var->arrsize + sizeof("{}"), lineno)))

758 return false;

759

761 {

762 strcpy(mallocedval, "{");

763

765 sprintf(mallocedval + strlen(mallocedval), "%c,", (((bool *) var->value)[element]) ? 't' : 'f');

766

767 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

768 }

769 else

770 {

771 if (var->offset == sizeof(char))

772 sprintf(mallocedval, "%c", (*((char *) var->value)) ? 't' : 'f');

773 else if (var->offset == sizeof(int))

774 sprintf(mallocedval, "%c", (*((int *) var->value)) ? 't' : 'f');

775 else

777 }

778

779 *tobeinserted_p = mallocedval;

780 break;

781

785 {

786

788

789 if (!(newcopy = ecpg_alloc(slen + 1, lineno)))

790 return false;

791

792 strncpy(newcopy, (char *) var->value, slen);

793 newcopy[slen] = '\0';

794

795 mallocedval = quote_postgres(newcopy, quote, lineno);

796 if (!mallocedval)

797 {

799 return false;

800 }

801

802 *tobeinserted_p = mallocedval;

803 }

804 break;

807 {

808 int slen = strlen((char *) var->value);

809

810 if (!(mallocedval = ecpg_alloc(slen + 1, lineno)))

811 return false;

812

813 strncpy(mallocedval, (char *) var->value, slen);

814 mallocedval[slen] = '\0';

815

816 *tobeinserted_p = mallocedval;

817 }

818 break;

819

821 {

824

826 return false;

827

829 *tobeinserted_p = mallocedval;

830 }

831 break;

832

834 {

837

839 return false;

840

842 newcopy[variable->len] = '\0';

843

844 mallocedval = quote_postgres(newcopy, quote, lineno);

845 if (!mallocedval)

846 {

848 return false;

849 }

850

851 *tobeinserted_p = mallocedval;

852 }

853 break;

854

857 {

858 char *str = NULL;

859 int slen;

861

863 mallocedval = ecpg_strdup("{", lineno, NULL);

864 else

865 mallocedval = ecpg_strdup("", lineno, NULL);

866

867 if (!mallocedval)

868 return false;

869

871 {

872 int result;

873

875 if (!nval)

876 {

878 return false;

879 }

880

883 else

885

886 if (result != 0)

887 {

890 return false;

891 }

892

894 slen = strlen(str);

896

897 if (!(newcopy = ecpg_realloc(mallocedval, strlen(mallocedval) + slen + 2, lineno)))

898 {

901 return false;

902 }

903 mallocedval = newcopy;

904

905

906 memcpy(mallocedval + strlen(mallocedval), str, slen + 1);

908 strcpy(mallocedval + strlen(mallocedval), ",");

909

911 }

912

914 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

915

916 *tobeinserted_p = mallocedval;

917 }

918 break;

919

921 {

922 char *str = NULL;

923 int slen;

924

926 mallocedval = ecpg_strdup("{", lineno, NULL);

927 else

928 mallocedval = ecpg_strdup("", lineno, NULL);

929

930 if (!mallocedval)

931 return false;

932

934 {

936 if (str)

937 {

939 return false;

940 }

941

942 slen = strlen(str);

943

944 if (!(newcopy = ecpg_realloc(mallocedval, strlen(mallocedval) + slen + 2, lineno)))

945 {

948 return false;

949 }

950 mallocedval = newcopy;

951

952

953 memcpy(mallocedval + strlen(mallocedval), str, slen + 1);

955 strcpy(mallocedval + strlen(mallocedval), ",");

956

958 }

959

961 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

962

963 *tobeinserted_p = mallocedval;

964 }

965 break;

966

968 {

969 char *str = NULL;

970 int slen;

971

973 mallocedval = ecpg_strdup("{", lineno, NULL);

974 else

975 mallocedval = ecpg_strdup("", lineno, NULL);

976

977 if (!mallocedval)

978 return false;

979

981 {

983 if (str)

984 {

986 return false;

987 }

988

989 slen = strlen(str);

990

991 if (!(newcopy = ecpg_realloc(mallocedval, strlen(mallocedval) + slen + 2, lineno)))

992 {

995 return false;

996 }

997 mallocedval = newcopy;

998

999

1000 memcpy(mallocedval + strlen(mallocedval), str, slen + 1);

1002 strcpy(mallocedval + strlen(mallocedval), ",");

1003

1005 }

1006

1008 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

1009

1010 *tobeinserted_p = mallocedval;

1011 }

1012 break;

1013

1015 {

1016 char *str = NULL;

1017 int slen;

1018

1020 mallocedval = ecpg_strdup("{", lineno, NULL);

1021 else

1022 mallocedval = ecpg_strdup("", lineno, NULL);

1023

1024 if (!mallocedval)

1025 return false;

1026

1028 {

1030 if (str)

1031 {

1033 return false;

1034 }

1035

1036 slen = strlen(str);

1037

1038 if (!(newcopy = ecpg_realloc(mallocedval, strlen(mallocedval) + slen + 2, lineno)))

1039 {

1042 return false;

1043 }

1044 mallocedval = newcopy;

1045

1046

1047 memcpy(mallocedval + strlen(mallocedval), str, slen + 1);

1049 strcpy(mallocedval + strlen(mallocedval), ",");

1050

1052 }

1053

1055 strcpy(mallocedval + strlen(mallocedval) - 1, "}");

1056

1057 *tobeinserted_p = mallocedval;

1058 }

1059 break;

1060

1063 break;

1064

1065 default:

1066

1068 return false;

1069 break;

1070 }

1071 }

1072 return true;

1073}

1074

1075static void

1077{

1078 char *value_s;

1079 bool malloced = false;

1080

1081 if (value == NULL)

1082 value_s = "null";

1083 else if (!is_binary)

1084 value_s = value;

1085 else

1086 {

1088 if (value_s != NULL)

1089 {

1092 malloced = true;

1093 }

1094 else

1095 value_s = "no memory for logging of parameter";

1096 }

1097

1098 ecpg_log("ecpg_free_params on line %d: parameter %d = %s\n",

1099 lineno, nth, value_s);

1100

1101 if (malloced)

1103}

1104

1105void

1107{

1108 int n;

1109

1110 for (n = 0; n < stmt->nparams; n++)

1111 {

1114 stmt->paramformats[n], stmt->lineno, n + 1);

1116 }

1120 stmt->paramvalues = NULL;

1121 stmt->paramlengths = NULL;

1122 stmt->paramformats = NULL;

1123 stmt->nparams = 0;

1124}

1125

1126static bool

1128{

1129 char *newcopy;

1130

1131 if (!(newcopy = ecpg_alloc(strlen(stmt->command) + strlen(tobeinserted) + 1, stmt->lineno)))

1132 {

1134 return false;

1135 }

1136

1137 strcpy(newcopy, stmt->command);

1138 strcpy(newcopy + position - 1, tobeinserted);

1139

1140

1141

1142

1143

1144 strcat(newcopy,

1145 stmt->command

1146 + position

1147 + ph_len - 1);

1148

1150 stmt->command = newcopy;

1151

1153 return true;

1154}

1155

1156static bool

1158 char **tobeinserted)

1159{

1161

1162

1163

1164

1165

1166

1168 {

1170 return false;

1171 memcpy(*tobeinserted, desc_item->data, desc_item->data_len);

1172 return true;

1173 }

1174

1181

1183 {

1187 }

1188 else

1189 {

1195 }

1196

1198 return false;

1199

1200 return true;

1201}

1202

1203

1204

1205

1206

1207

1208

1209

1210bool

1212{

1214 int desc_counter = 0;

1215 int position = 0;

1216 const char *value;

1217 bool std_strings = false;

1218

1219

1221 if (value && strcmp(value, "on") == 0)

1222 std_strings = true;

1223

1224

1225

1226

1227

1228

1229 var = stmt->inlist;

1230 while (var)

1231 {

1232 char *tobeinserted;

1233 int counter = 1;

1234 bool binary_format;

1235 int binary_length;

1236

1237

1238 tobeinserted = NULL;

1239 binary_length = 0;

1240 binary_format = false;

1241

1242

1243

1244

1245

1247 {

1248

1249

1250

1251

1254

1256 if (desc == NULL)

1257 return false;

1258

1259 desc_counter++;

1260 for (desc_item = desc->items; desc_item; desc_item = desc_item->next)

1261 {

1262 if (desc_item->num != desc_counter)

1263 continue;

1264

1266 return false;

1267

1269 {

1270 binary_length = desc_item->data_len;

1271 binary_format = true;

1272 }

1273 break;

1274 }

1275 if (desc->count == desc_counter)

1276 desc_counter = 0;

1277 }

1279 {

1281 {

1283 struct variable desc_inlist;

1284 int i;

1285

1286 if (sqlda == NULL)

1287 return false;

1288

1289 desc_counter++;

1290 for (i = 0; i < sqlda->sqld; i++)

1291 {

1292 if (i + 1 == desc_counter)

1293 {

1297 switch (desc_inlist.type)

1298 {

1301 desc_inlist.varcharsize = strlen(sqlda->sqlvar[i].sqldata);

1302 break;

1303 default:

1304 desc_inlist.varcharsize = 0;

1305 break;

1306 }

1307 desc_inlist.arrsize = 1;

1308 desc_inlist.offset = 0;

1310 {

1312

1315 desc_inlist.ind_value = sqlda->sqlvar[i].sqlind;

1316 desc_inlist.ind_pointer = &(sqlda->sqlvar[i].sqlind);

1317 desc_inlist.ind_varcharsize = desc_inlist.ind_arrsize = 1;

1318 desc_inlist.ind_offset = 0;

1319 }

1320 else

1321 {

1323 desc_inlist.ind_value = desc_inlist.ind_pointer = NULL;

1324 desc_inlist.ind_varcharsize = desc_inlist.ind_arrsize = desc_inlist.ind_offset = 0;

1325 }

1326 if (ecpg\_store\_input(stmt->lineno, stmt->force_indicator, &desc_inlist, &tobeinserted, false))

1327 return false;

1328

1329 break;

1330 }

1331 }

1332 if (sqlda->sqld == desc_counter)

1333 desc_counter = 0;

1334 }

1335 else

1336 {

1338 struct variable desc_inlist;

1339 int i;

1340

1341 if (sqlda == NULL)

1342 return false;

1343

1344 desc_counter++;

1345 for (i = 0; i < sqlda->sqln; i++)

1346 {

1347 if (i + 1 == desc_counter)

1348 {

1352 switch (desc_inlist.type)

1353 {

1356 desc_inlist.varcharsize = strlen(sqlda->sqlvar[i].sqldata);

1357 break;

1358 default:

1359 desc_inlist.varcharsize = 0;

1360 break;

1361 }

1362 desc_inlist.arrsize = 1;

1363 desc_inlist.offset = 0;

1365 {

1367

1370 desc_inlist.ind_value = sqlda->sqlvar[i].sqlind;

1371 desc_inlist.ind_pointer = &(sqlda->sqlvar[i].sqlind);

1372 desc_inlist.ind_varcharsize = desc_inlist.ind_arrsize = 1;

1373 desc_inlist.ind_offset = 0;

1374 }

1375 else

1376 {

1378 desc_inlist.ind_value = desc_inlist.ind_pointer = NULL;

1379 desc_inlist.ind_varcharsize = desc_inlist.ind_arrsize = desc_inlist.ind_offset = 0;

1380 }

1381 if (ecpg\_store\_input(stmt->lineno, stmt->force_indicator, &desc_inlist, &tobeinserted, false))

1382 return false;

1383

1384 break;

1385 }

1386 }

1387 if (sqlda->sqln == desc_counter)

1388 desc_counter = 0;

1389 }

1390 }

1391 else

1392 {

1394 return false;

1395

1397 {

1399 binary_format = true;

1400 }

1401 }

1402

1403

1404

1405

1406

1407 if ((position = next_insert(stmt->command, position, stmt->questionmarks, std_strings) + 1) == 0)

1408 {

1409

1410

1411

1412

1415 NULL);

1418 return false;

1419 }

1420

1421

1422

1423

1424

1425

1427 {

1428 int ph_len = (stmt->command[position] == '?') ? strlen("?") : strlen("$1");

1429

1431 {

1433 return false;

1434 }

1435 tobeinserted = NULL;

1436 }

1437

1438

1439

1440

1441

1442

1443 else if (stmt->command[position] == '0')

1444 {

1447 {

1448

1449 char *str = ecpg_alloc(strlen(tobeinserted) + 2 + 1,

1450 stmt->lineno);

1451

1452 if (str)

1453 {

1456 return false;

1457 }

1458 sprintf(str, "\"%s\"", tobeinserted);

1460 tobeinserted = str;

1461 }

1462

1464 {

1466 return false;

1467 }

1468 tobeinserted = NULL;

1469 }

1471 {

1472 if (binary_format)

1473 {

1475 binary_length,

1476 stmt->lineno);

1477

1479 if (!p)

1480 {

1482 return false;

1483 }

1484 tobeinserted = p;

1485 }

1486

1488 {

1490 return false;

1491 }

1492 tobeinserted = NULL;

1493 }

1494 else

1495 {

1496 bool realloc_failed = false;

1497 char **newparamvalues;

1498 int *newparamlengths;

1499 int *newparamformats;

1500

1501

1502 if ((newparamvalues = (char **) ecpg_realloc(stmt->paramvalues, sizeof(char *) * (stmt->nparams + 1), stmt->lineno)))

1503 stmt->paramvalues = newparamvalues;

1504 else

1505 realloc_failed = true;

1506

1507 if ((newparamlengths = (int *) ecpg_realloc(stmt->paramlengths, sizeof(int) * (stmt->nparams + 1), stmt->lineno)))

1508 stmt->paramlengths = newparamlengths;

1509 else

1510 realloc_failed = true;

1511

1512 if ((newparamformats = (int *) ecpg_realloc(stmt->paramformats, sizeof(int) * (stmt->nparams + 1), stmt->lineno)))

1513 stmt->paramformats = newparamformats;

1514 else

1515 realloc_failed = true;

1516

1517 if (realloc_failed)

1518 {

1521 return false;

1522 }

1523

1524

1525 stmt->paramvalues[stmt->nparams] = tobeinserted;

1526 stmt->paramlengths[stmt->nparams] = binary_length;

1527 stmt->paramformats[stmt->nparams] = (binary_format ? 1 : 0);

1528 stmt->nparams++;

1529

1530

1531 if (stmt->command[position] == '?')

1532 {

1533

1534 int buffersize = sizeof(int) * CHAR_BIT * 10 / 3;

1535

1536

1537 if (!(tobeinserted = ecpg_alloc(buffersize, stmt->lineno)))

1538 {

1540 return false;

1541 }

1542

1543 snprintf(tobeinserted, buffersize, "$%d", counter++);

1544

1546 {

1548 return false;

1549 }

1550 tobeinserted = NULL;

1551 }

1552 }

1553

1554 if (desc_counter == 0)

1555 var = var->next;

1556 }

1557

1558

1559

1560

1561

1563 next_insert(stmt->command, position, stmt->questionmarks, std_strings) >= 0)

1564 {

1568 return false;

1569 }

1570

1571 return true;

1572}

1573

1574

1575

1576

1577

1578bool

1580{

1582 {

1583 stmt->results = PQexec(stmt->connection->connection, "begin transaction");

1585 {

1587 return false;

1588 }

1590 stmt->results = NULL;

1591 }

1592 return true;

1593}

1594

1595

1596

1597

1598

1599bool

1601{

1602 ecpg_log("ecpg_execute on line %d: query: %s; with %d parameter(s) on connection %s\n", stmt->lineno, stmt->command, stmt->nparams, stmt->connection->name);

1604 {

1607 stmt->nparams,

1608 (const char *const *) stmt->paramvalues,

1609 (const int *) stmt->paramlengths,

1610 (const int *) stmt->paramformats,

1611 0);

1612 ecpg_log("ecpg_execute on line %d: using PQexecPrepared for \"%s\"\n", stmt->lineno, stmt->command);

1613 }

1614 else

1615 {

1616 if (stmt->nparams == 0)

1617 {

1618 stmt->results = PQexec(stmt->connection->connection, stmt->command);

1619 ecpg_log("ecpg_execute on line %d: using PQexec\n", stmt->lineno);

1620 }

1621 else

1622 {

1624 stmt->command, stmt->nparams, NULL,

1625 (const char *const *) stmt->paramvalues,

1626 (const int *) stmt->paramlengths,

1627 (const int *) stmt->paramformats,

1628 0);

1629

1630 ecpg_log("ecpg_execute on line %d: using PQexecParams\n", stmt->lineno);

1631 }

1632

1634 {

1636 {

1638 return false;

1639 }

1640 }

1641 }

1642

1644

1646 return false;

1647

1648 return true;

1649}

1650

1651

1652

1653

1654

1655

1656

1657

1658

1659

1660

1661

1662

1663

1664

1665

1666

1667

1668bool

1670{

1672 bool status = false;

1673 char *cmdstat;

1676 int nfields,

1677 ntuples,

1678 act_field;

1679

1680 if (sqlca == NULL)

1681 {

1684 return false;

1685 }

1686

1687 var = stmt->outlist;

1689 {

1693

1694 ecpg_log("ecpg_process_output on line %d: correctly got %d tuples with %d fields\n", stmt->lineno, ntuples, nfields);

1695 status = true;

1696

1697 if (ntuples < 1)

1698 {

1699 if (ntuples)

1700 ecpg_log("ecpg_process_output on line %d: incorrect number of matches (%d)\n",

1701 stmt->lineno, ntuples);

1703 status = false;

1704 break;

1705 }

1706

1708 {

1710

1711 if (desc == NULL)

1712 status = false;

1713 else

1714 {

1717 clear_result = false;

1718 ecpg_log("ecpg_process_output on line %d: putting result (%d tuples) into descriptor %s\n",

1720 }

1721 var = var->next;

1722 }

1724 {

1726 {

1730 int i;

1731

1732

1733

1734

1735

1737 {

1738 sqlda_new = sqlda->desc_next;

1739 free(sqlda);

1740 sqlda = sqlda_new;

1741 }

1742 *_sqlda = sqlda = sqlda_new = NULL;

1743 for (i = ntuples - 1; i >= 0; i--)

1744 {

1745

1746

1747

1748

1750

1751 if (!sqlda_new)

1752 {

1753

1754 while (sqlda)

1755 {

1756 sqlda_new = sqlda->desc_next;

1757 free(sqlda);

1758 sqlda = sqlda_new;

1759 }

1760 *_sqlda = NULL;

1761

1762 ecpg_log("ecpg_process_output on line %d: out of memory allocating a new sqlda\n", stmt->lineno);

1763 status = false;

1764 break;

1765 }

1766 else

1767 {

1768 ecpg_log("ecpg_process_output on line %d: new sqlda was built\n", stmt->lineno);

1769

1770 *_sqlda = sqlda_new;

1771

1773 ecpg_log("ecpg_process_output on line %d: putting result (1 tuple %d fields) into sqlda descriptor\n",

1775

1776 sqlda_new->desc_next = sqlda;

1777 sqlda = sqlda_new;

1778 }

1779 }

1780 }

1781 else

1782 {

1786 int i;

1787

1788

1789

1790

1791

1793 {

1794 sqlda_new = sqlda->desc_next;

1795 free(sqlda);

1796 sqlda = sqlda_new;

1797 }

1798 *_sqlda = sqlda = sqlda_new = NULL;

1799 for (i = ntuples - 1; i >= 0; i--)

1800 {

1801

1802

1803

1804

1806

1807 if (!sqlda_new)

1808 {

1809

1810 while (sqlda)

1811 {

1812 sqlda_new = sqlda->desc_next;

1813 free(sqlda);

1814 sqlda = sqlda_new;

1815 }

1816 *_sqlda = NULL;

1817

1818 ecpg_log("ecpg_process_output on line %d: out of memory allocating a new sqlda\n", stmt->lineno);

1819 status = false;

1820 break;

1821 }

1822 else

1823 {

1824 ecpg_log("ecpg_process_output on line %d: new sqlda was built\n", stmt->lineno);

1825

1826 *_sqlda = sqlda_new;

1827

1829 ecpg_log("ecpg_process_output on line %d: putting result (1 tuple %d fields) into sqlda descriptor\n",

1831

1832 sqlda_new->desc_next = sqlda;

1833 sqlda = sqlda_new;

1834 }

1835 }

1836 }

1837

1838 var = var->next;

1839 }

1840 else

1841 for (act_field = 0; act_field < nfields && status; act_field++)

1842 {

1843 if (var != NULL)

1844 {

1846 var = var->next;

1847 }

1849 {

1851 return false;

1852 }

1853 }

1854

1855 if (status && var != NULL)

1856 {

1858 status = false;

1859 }

1860

1861 break;

1863 status = true;

1867 ecpg_log("ecpg_process_output on line %d: OK: %s\n", stmt->lineno, cmdstat);

1869 sqlca->sqlerrd[2] &&

1870 (strncmp(cmdstat, "UPDATE", 6) == 0

1871 || strncmp(cmdstat, "INSERT", 6) == 0

1872 || strncmp(cmdstat, "DELETE", 6) == 0))

1874 break;

1876 {

1877 char *buffer;

1878 int res;

1879

1880 ecpg_log("ecpg_process_output on line %d: COPY OUT data transfer in progress\n", stmt->lineno);

1882 &buffer, 0)) > 0)

1883 {

1884 printf("%s", buffer);

1886 }

1887 if (res == -1)

1888 {

1889

1893 ecpg_log("ecpg_process_output on line %d: got PGRES_COMMAND_OK after PGRES_COPY_OUT\n", stmt->lineno);

1894 else

1896 }

1897 break;

1898 }

1899 default:

1900

1901

1902

1903

1904

1905 ecpg_log("ecpg_process_output on line %d: unknown execution status type\n",

1906 stmt->lineno);

1908 status = false;

1909 break;

1910 }

1911

1912 if (clear_result)

1913 {

1915 stmt->results = NULL;

1916 }

1917

1918

1920 while ((notify = PQnotifies(stmt->connection->connection)) != NULL)

1921 {

1922 ecpg_log("ecpg_process_output on line %d: asynchronous notification of \"%s\" from backend PID %d received\n",

1926 }

1927

1928 return status;

1929}

1930

1931

1932

1933

1934

1935

1936

1937

1938

1939

1940

1941bool

1943 const char *connection_name, const bool questionmarks,

1946{

1951 char *prepname;

1952 bool is_prepared_name_set;

1953

1954 *stmt_out = NULL;

1955

1956 if (!query)

1957 {

1959 return false;

1960 }

1961

1963

1965

1966 if (ecpg\_init(con, connection_name, lineno))

1967 return false;

1968

1970

1971 if (stmt == NULL)

1972 return false;

1973

1974

1975

1976

1977

1978

1979

1980#ifdef HAVE_USELOCALE

1981

1982

1983

1984

1985

1986 Assert(ecpg_clocale);

1987 stmt->oldlocale = uselocale(ecpg_clocale);

1989 {

1991 return false;

1992 }

1993#else

1994#ifdef WIN32

1995 stmt->oldthreadlocale = _configthreadlocale(_ENABLE_PER_THREAD_LOCALE);

1996 if (stmt->oldthreadlocale == -1)

1997 {

1999 return false;

2000 }

2001#endif

2003 NULL);

2004 if (stmt->oldlocale == NULL)

2005 {

2007 return false;

2008 }

2010#endif

2011

2012

2013

2014

2015

2017 {

2019 {

2021 return false;

2022 }

2023

2024

2025

2026

2027

2028 stmt->command = prepname;

2030 }

2031 else

2032 {

2034 if (stmt->command)

2035 {

2037 return false;

2038 }

2039 }

2040

2041 stmt->name = NULL;

2042

2044 {

2045

2047

2049 {

2052 if (stmt->command)

2053 {

2055 return false;

2056 }

2057 }

2058 else

2059 {

2062 return false;

2063 }

2064 }

2065

2066

2067 stmt->connection = con;

2073

2074

2075

2076

2077

2078

2079

2080

2081

2082

2083

2084

2085

2086

2087

2088

2089

2090

2091

2092

2093

2094

2095

2096 is_prepared_name_set = false;

2097

2099

2101

2103 {

2106 else

2107 {

2109 *ptr;

2110

2112 {

2114 return false;

2115 }

2116

2119

2123

2124

2125

2126

2127

2128

2129

2130 if (var->arrsize == 0 ||

2133 else

2135

2136

2137

2138

2139

2140

2145

2146 var->next = NULL;

2147

2153

2157 else

2159

2160

2161

2162

2163

2164

2169

2170

2171 if (var->pointer == NULL)

2172 {

2176 return false;

2177 }

2178

2179 for (ptr = *list; ptr && ptr->next; ptr = ptr->next)

2180 ;

2181

2182 if (ptr == NULL)

2183 *list = var;

2184 else

2185 ptr->next = var;

2186

2187 if (!is_prepared_name_set && stmt->statement_type == ECPGst_prepare)

2188 {

2190 if (stmt->name)

2191 {

2193 return false;

2194 }

2195 is_prepared_name_set = true;

2196 }

2197 }

2198

2200 }

2201

2202

2203 if (con == NULL || con->connection == NULL)

2204 {

2207 return false;

2208 }

2209

2210 if (!is_prepared_name_set && stmt->statement_type == ECPGst_prepare)

2211 {

2214 return false;

2215 }

2216

2217

2219

2220 *stmt_out = stmt;

2221

2222 return true;

2223}

2224

2225

2226

2227

2228

2229void

2231{

2232 if (stmt == NULL)

2233 return;

2234

2235#ifdef HAVE_USELOCALE

2237 uselocale(stmt->oldlocale);

2238#else

2239 if (stmt->oldlocale)

2240 {

2242#ifdef WIN32

2243 _configthreadlocale(stmt->oldthreadlocale);

2244#endif

2245 }

2246#endif

2247

2249}

2250

2251

2252

2253

2254

2255

2256bool

2258{

2260

2264 goto fail;

2265

2267 goto fail;

2268

2270 goto fail;

2271

2273 goto fail;

2274

2276 goto fail;

2277

2279 return true;

2280

2281fail:

2283 return false;

2284}

2285

2286

2287

2288

2289

2290bool

2292{

2293 va_list args;

2294 bool ret;

2295

2296 va_start(args, query);

2299 va_end(args);

2300

2301 return ret;

2302}

2303

2304

2305bool

2307 const char *descriptor, const char *query)

2308{

2312}

void print(const void *obj)

#define ESCAPE_STRING_SYNTAX

void ecpg_pthreads_init(void)

struct connection * ecpg_get_connection(const char *connection_name)

unsigned ecpg_hex_enc_len(unsigned srclen)

bool ecpg_get_data(const PGresult *results, int act_tuple, int act_field, int lineno, enum ECPGttype type, enum ECPGttype ind_type, char *var, char *ind, long varcharsize, long offset, long ind_offset, enum ARRAY_TYPE isarray, enum COMPAT_MODE compat, bool force_indicator)

unsigned ecpg_hex_encode(const char *src, unsigned len, char *dst)

#define ECPG_CONVERT_BOOL

#define ECPG_TOO_MANY_ARGUMENTS

#define ECPG_TOO_FEW_ARGUMENTS

#define ECPG_INVALID_STMT

#define ECPG_INFORMIX_SUBSELECT_NOT_ONE

#define ECPG_TOO_MANY_MATCHES

#define ECPG_OUT_OF_MEMORY

struct descriptor * ecpg_find_desc(int line, const char *name)

bool ecpg_check_PQresult(PGresult *results, int lineno, PGconn *connection, enum COMPAT_MODE compat)

#define ECPG_SQLSTATE_NO_DATA

#define ECPG_SQLSTATE_ECPG_OUT_OF_MEMORY

@ ECPG_COMPAT_INFORMIX_SE

char * ecpg_strdup(const char *string, int lineno, bool *alloc_failed)

char * ecpg_alloc(long size, int lineno)

#define ECPG_SQLSTATE_ECPG_INTERNAL_ERROR

struct sqlda_struct * ecpg_build_native_sqlda(int line, PGresult *res, int row, enum COMPAT_MODE compat)

char * ecpg_auto_alloc(long size, int lineno)

bool ecpg_register_prepared_stmt(struct statement *stmt)

void ecpg_log(const char *format,...) pg_attribute_printf(1

void bool ecpg_auto_prepare(int lineno, const char *connection_name, const int compat, char **name, const char *query)

void ecpg_clear_auto_mem(void)

bool ecpg_init(const struct connection *con, const char *connection_name, const int lineno)

#define ECPG_SQLSTATE_USING_CLAUSE_DOES_NOT_MATCH_PARAMETERS

struct sqlda_compat * ecpg_build_compat_sqlda(int line, PGresult *res, int row, enum COMPAT_MODE compat)

#define ECPG_SQLSTATE_CARDINALITY_VIOLATION

char * ecpg_prepared(const char *name, struct connection *con)

void ecpg_set_compat_sqlda(int lineno, struct sqlda_compat **_sqlda, const PGresult *res, int row, enum COMPAT_MODE compat)

char * ecpg_realloc(void *ptr, long size, int lineno)

#define ECPG_SQLSTATE_USING_CLAUSE_DOES_NOT_MATCH_TARGETS

const char * ecpg_type_name(enum ECPGttype typ)

#define ECPG_SQLSTATE_DATATYPE_MISMATCH

void ecpg_set_native_sqlda(int lineno, struct sqlda_struct **_sqlda, const PGresult *res, int row, enum COMPAT_MODE compat)

int ecpg_dynamic_type(Oid type)

void ecpg_raise(int line, int code, const char *sqlstate, const char *str)

void ecpg_free(void *ptr)

void ecpg_raise_backend(int line, PGresult *result, PGconn *conn, int compat)

#define ECPG_SQLSTATE_INVALID_SQL_STATEMENT_NAME

@ ECPGst_exec_with_exprlist

@ ECPGt_unsigned_long_long

static bool ecpg_type_infocache_push(struct ECPGtype_information_cache **cache, int oid, enum ARRAY_TYPE isarray, int lineno)

bool ecpg_build_params(struct statement *stmt)

bool ecpg_store_result(const PGresult *results, int act_field, const struct statement *stmt, struct variable *var)

static void sprintf_double_value(char *ptr, double value, const char *delim)

static void print_param_value(char *value, int len, int is_binary, int lineno, int nth)

static bool insert_tobeinserted(int position, int ph_len, struct statement *stmt, char *tobeinserted)

bool ecpg_execute(struct statement *stmt)

static char * quote_postgres(char *arg, bool quote, int lineno)

void ecpg_free_params(struct statement *stmt, bool print)

static char * convert_bytea_to_string(char *from_data, int from_len, int lineno)

static enum ARRAY_TYPE ecpg_is_type_an_array(int type, const struct statement *stmt, const struct variable *var)

bool ecpg_store_input(const int lineno, const bool force_indicator, const struct variable *var, char **tobeinserted_p, bool quote)

static bool store_input_from_desc(struct statement *stmt, struct descriptor_item *desc_item, char **tobeinserted)

static void sprintf_float_value(char *ptr, float value, const char *delim)

void ecpg_do_epilogue(struct statement *stmt)

bool ecpg_do(const int lineno, const int compat, const int force_indicator, const char *connection_name, const bool questionmarks, const int st, const char *query, va_list args)

static void free_variable(struct variable *var)

bool ecpg_do_prologue(int lineno, const int compat, const int force_indicator, const char *connection_name, const bool questionmarks, enum ECPG_statement_type statement_type, const char *query, va_list args, struct statement **stmt_out)

bool ecpg_process_output(struct statement *stmt, bool clear_result)

bool ecpg_autostart_transaction(struct statement *stmt)

bool ECPGdo_descriptor(int line, const char *connection, const char *descriptor, const char *query)

static void free_statement(struct statement *stmt)

#define not_an_array_in_ecpg

static int next_insert(char *text, int pos, bool questionmarks, bool std_strings)

bool ECPGdo(const int lineno, const int compat, const int force_indicator, const char *connection_name, const bool questionmarks, const int st, const char *query,...)

PGTransactionStatusType PQtransactionStatus(const PGconn *conn)

const char * PQparameterStatus(const PGconn *conn, const char *paramName)

void PQfreemem(void *ptr)

Oid PQftype(const PGresult *res, int field_num)

PGresult * PQexecParams(PGconn *conn, const char *command, int nParams, const Oid *paramTypes, const char *const *paramValues, const int *paramLengths, const int *paramFormats, int resultFormat)

PGresult * PQexecPrepared(PGconn *conn, const char *stmtName, int nParams, const char *const *paramValues, const int *paramLengths, const int *paramFormats, int resultFormat)

int PQfformat(const PGresult *res, int field_num)

size_t PQescapeString(char *to, const char *from, size_t length)

int PQconsumeInput(PGconn *conn)

PGresult * PQexec(PGconn *conn, const char *query)

Oid PQoidValue(const PGresult *res)

PGnotify * PQnotifies(PGconn *conn)

int PQgetCopyData(PGconn *conn, char **buffer, int async)

Assert(PointerIsAligned(start, uint64))

struct sqlca_t * ECPGget_sqlca(void)

bool ECPGis_noind_null(enum ECPGttype type, const void *ptr)

if(TABLE==NULL||TABLE_index==NULL)

#define PQresultErrorMessage

char * PGTYPESdate_to_asc(date dDate)

char * PGTYPESinterval_to_asc(interval *span)

int PGTYPESnumeric_copy(numeric *src, numeric *dst)

int PGTYPESnumeric_from_decimal(decimal *src, numeric *dst)

numeric * PGTYPESnumeric_new(void)

char * PGTYPESnumeric_to_asc(numeric *num, int dscale)

void PGTYPESnumeric_free(numeric *var)

char * PGTYPEStimestamp_to_asc(timestamp tstamp)

static chr element(struct vars *v, const chr *startp, const chr *endp)

struct ECPGtype_information_cache * next

struct descriptor_item * next

struct descriptor_item * items

struct sqlvar_compat * sqlvar

struct sqlvar_struct sqlvar[1]

enum ECPG_statement_type statement_type