00001
00002
00003 #include "postgres_fe.h"
00004
00005 #include "extern.h"
00006
00007 static void output_escaped_str(char *cmd, bool quoted);
00008
00009 void
00010 output_line_number(void)
00011 {
00012 char *line = hashline_number();
00013
00014 fprintf(yyout, "%s", line);
00015 free(line);
00016 }
00017
00018 void
00019 output_simple_statement(char *stmt)
00020 {
00021 output_escaped_str(stmt, false);
00022 output_line_number();
00023 free(stmt);
00024 }
00025
00026
00027
00028
00029
00030 struct when when_error,
00031 when_nf,
00032 when_warn;
00033
00034 static void
00035 print_action(struct when * w)
00036 {
00037 switch (w->code)
00038 {
00039 case W_SQLPRINT:
00040 fprintf(yyout, "sqlprint();");
00041 break;
00042 case W_GOTO:
00043 fprintf(yyout, "goto %s;", w->command);
00044 break;
00045 case W_DO:
00046 fprintf(yyout, "%s;", w->command);
00047 break;
00048 case W_STOP:
00049 fprintf(yyout, "exit (1);");
00050 break;
00051 case W_BREAK:
00052 fprintf(yyout, "break;");
00053 break;
00054 default:
00055 fprintf(yyout, "{/* %d not implemented yet */}", w->code);
00056 break;
00057 }
00058 }
00059
00060 void
00061 whenever_action(int mode)
00062 {
00063 if ((mode & 1) == 1 && when_nf.code != W_NOTHING)
00064 {
00065 output_line_number();
00066 fprintf(yyout, "\nif (sqlca.sqlcode == ECPG_NOT_FOUND) ");
00067 print_action(&when_nf);
00068 }
00069 if (when_warn.code != W_NOTHING)
00070 {
00071 output_line_number();
00072 fprintf(yyout, "\nif (sqlca.sqlwarn[0] == 'W') ");
00073 print_action(&when_warn);
00074 }
00075 if (when_error.code != W_NOTHING)
00076 {
00077 output_line_number();
00078 fprintf(yyout, "\nif (sqlca.sqlcode < 0) ");
00079 print_action(&when_error);
00080 }
00081
00082 if ((mode & 2) == 2)
00083 fputc('}', yyout);
00084
00085 output_line_number();
00086 }
00087
00088 char *
00089 hashline_number(void)
00090 {
00091
00092 if (input_filename
00093 #ifdef YYDEBUG
00094 && !yydebug
00095 #endif
00096 )
00097 {
00098 char *line = mm_alloc(strlen("\n#line %d \"%s\"\n") + sizeof(int) * CHAR_BIT * 10 / 3 + strlen(input_filename));
00099
00100 sprintf(line, "\n#line %d \"%s\"\n", yylineno, input_filename);
00101
00102 return line;
00103 }
00104
00105 return EMPTY;
00106 }
00107
00108 static char *ecpg_statement_type_name[] = {
00109 "ECPGst_normal",
00110 "ECPGst_execute",
00111 "ECPGst_exec_immediate",
00112 "ECPGst_prepnormal"
00113 };
00114
00115 void
00116 output_statement(char *stmt, int whenever_mode, enum ECPG_statement_type st)
00117 {
00118 fprintf(yyout, "{ ECPGdo(__LINE__, %d, %d, %s, %d, ", compat, force_indicator, connection ? connection : "NULL", questionmarks);
00119 if (st == ECPGst_execute || st == ECPGst_exec_immediate)
00120 {
00121 fprintf(yyout, "%s, %s, ", ecpg_statement_type_name[st], stmt);
00122 }
00123 else
00124 {
00125 if (st == ECPGst_prepnormal && auto_prepare)
00126 fputs("ECPGst_prepnormal, \"", yyout);
00127 else
00128 fputs("ECPGst_normal, \"", yyout);
00129
00130 output_escaped_str(stmt, false);
00131 fputs("\", ", yyout);
00132 }
00133
00134
00135 dump_variables(argsinsert, 1);
00136 fputs("ECPGt_EOIT, ", yyout);
00137 dump_variables(argsresult, 1);
00138 fputs("ECPGt_EORT);", yyout);
00139 reset_variables();
00140
00141 whenever_action(whenever_mode | 2);
00142 free(stmt);
00143 if (connection != NULL)
00144 free(connection);
00145 }
00146
00147 void
00148 output_prepare_statement(char *name, char *stmt)
00149 {
00150 fprintf(yyout, "{ ECPGprepare(__LINE__, %s, %d, ", connection ? connection : "NULL", questionmarks);
00151 output_escaped_str(name, true);
00152 fputs(", ", yyout);
00153 output_escaped_str(stmt, true);
00154 fputs(");", yyout);
00155 whenever_action(2);
00156 free(name);
00157 if (connection != NULL)
00158 free(connection);
00159 }
00160
00161 void
00162 output_deallocate_prepare_statement(char *name)
00163 {
00164 const char *con = connection ? connection : "NULL";
00165
00166 if (strcmp(name, "all") != 0)
00167 {
00168 fprintf(yyout, "{ ECPGdeallocate(__LINE__, %d, %s, ", compat, con);
00169 output_escaped_str(name, true);
00170 fputs(");", yyout);
00171 }
00172 else
00173 fprintf(yyout, "{ ECPGdeallocate_all(__LINE__, %d, %s);", compat, con);
00174
00175 whenever_action(2);
00176 free(name);
00177 if (connection != NULL)
00178 free(connection);
00179 }
00180
00181 static void
00182 output_escaped_str(char *str, bool quoted)
00183 {
00184 int i = 0;
00185 int len = strlen(str);
00186
00187 if (quoted && str[0] == '\"' && str[len - 1] == '\"')
00188
00189
00190 {
00191 i = 1;
00192 len--;
00193 fputs("\"", yyout);
00194 }
00195
00196
00197 for (; i < len; i++)
00198 {
00199 if (str[i] == '"')
00200 fputs("\\\"", yyout);
00201 else if (str[i] == '\n')
00202 fputs("\\\n", yyout);
00203 else if (str[i] == '\\')
00204 {
00205 int j = i;
00206
00207
00208
00209
00210
00211
00212
00213 do
00214 {
00215 j++;
00216 } while (str[j] == ' ' || str[j] == '\t');
00217
00218 if ((str[j] != '\n') && (str[j] != '\r' || str[j + 1] != '\n'))
00219
00220 fputs("\\\\", yyout);
00221 }
00222 else if (str[i] == '\r' && str[i + 1] == '\n')
00223 {
00224 fputs("\\\r\n", yyout);
00225 i++;
00226 }
00227 else
00228 fputc(str[i], yyout);
00229 }
00230
00231 if (quoted && str[0] == '\"' && str[len] == '\"')
00232 fputs("\"", yyout);
00233 }