a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
041296 | 2009-01-19 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
7ac2f1 | 2008-07-27 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
4e1d1f | 2008-08-01 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
4e1d1f | 2008-08-01 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
4e1d1f | 2008-08-01 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
26c0ad | 2009-02-28 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
4e1d1f | 2008-08-01 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
041296 | 2009-01-19 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
4e1d1f | 2008-08-01 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
#pike __REAL_VERSION__
|
ecbab1 | 2008-07-27 | Stephen R. van den Berg | | #include "pgsql.h"
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
e22cab | 2008-07-14 | Stephen R. van den Berg | | #define ERROR(X ...) predef::error(X)
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | protected int fetchlimit=FETCHLIMIT;
protected Thread.Mutex unnamedportalmux,unnamedstatement;
int _portalsinflight;
protected .pgsql_util.PGassist c;
protected string cancelsecret;
protected int backendpid;
protected int backendstatus;
mapping(string:mixed) options;
protected array(string) lastmessage=({});
protected int clearmessage;
protected mapping(string:array(mixed)) notifylist=([]);
|
26c0ad | 2009-02-28 | Stephen R. van den Berg | | mapping(string:string) _runtimeparameter;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | protected enum querystate {
streconnect,reconnectforce,queryidle,inquery,cancelpending,canceled};
protected querystate qstate;
protected mapping(string:mapping(string:mixed)) prepareds=([]);
protected int pstmtcount;
protected int ptstmtcount;
int _pportalcount;
protected int totalhits;
protected int cachedepth=STATEMENTCACHEDEPTH;
protected int timeout=QUERYTIMEOUT;
protected int portalbuffersize=PORTALBUFFERSIZE;
protected int reconnected;
protected int reconnectdelay;
#ifdef PG_STATS
protected int skippeddescribe;
protected int portalsopened;
#endif
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | | int _msgsreceived;
int _bytesreceived;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | protected int warningsdropcount;
protected int prepstmtused;
protected int warningscollected;
protected int invalidatecache;
protected Thread.Queue qportals;
mixed _delayederror;
protected function (:void) readyforquery_cb;
string _host;
protected string database, user, pass;
int _port;
protected multiset cachealways=(<"BEGIN","begin","END","end","COMMIT","commit">);
protected object createprefix
|
9f4028 | 2008-08-27 | Stephen R. van den Berg | | =Regexp("^[ \t\f\r\n]*[Cc][Rr][Ee][Aa][Tt][Ee][ \t\f\r\n]");
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | protected object dontcacheprefix
|
928713 | 2008-09-03 | Stephen R. van den Berg | | =Regexp("^[ \t\f\r\n]*([Ff][Ee][Tt][Cc][Hh]|[Cc][Oo][Pp][Yy])[ \t\f\r\n]");
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | protected object execfetchlimit
|
a7a2d6 | 2012-04-04 | Stephen R. van den Berg | | =Regexp("^[ \t\f\r\n]*(([Uu][Pp][Dd][Aa]|[Dd][Ee][Ll][Ee])[Tt][Ee]|\
[Ii][Nn][Ss][Ee][Rr][Tt])[ \t\f\r\n]|\
[ \t\f\r\n][Ll][Ii][Mm][Ii][Tt][ \t\f\r\n]+[12][; \t\f\r\n]*$");
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | protected Thread.Mutex waitforauth;
protected Thread.Condition waitforauthready;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | #define DERROR(msg ...) ({sprintf(msg),backtrace()})
#define SERROR(msg ...) (sprintf(msg))
#define USERERROR(msg) throw(msg)
#define SUSERERROR(msg ...) USERERROR(SERROR(msg))
|
928713 | 2008-09-03 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | protected string _sprintf(int type, void|mapping flags) {
|
443c1f | 2014-08-21 | Stephen R. van den Berg | | string res=UNDEFINED;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | switch(type) {
case 'O':
res=sprintf(DRIVERNAME"(%s@%s:%d/%s,%d)",
user,_host,_port,database,backendpid);
break;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
return res;
}
#define BOOLOID 16
#define BYTEAOID 17
#define CHAROID 18
#define INT8OID 20
#define INT2OID 21
#define INT4OID 23
#define TEXTOID 25
#define OIDOID 26
#define XMLOID 142
#define FLOAT4OID 700
|
05bf88 | 2008-08-26 | Stephen R. van den Berg | | #define FLOAT8OID 701
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | #define MACADDROID 829
|
7c4bd0 | 2008-08-09 | Stephen R. van den Berg | | #define INETOID 869 /* Force textmode */
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | #define BPCHAROID 1042
#define VARCHAROID 1043
#define CTIDOID 1247
#define UUIDOID 2950
|
26c0ad | 2009-02-28 | Stephen R. van den Berg | | #define UTF8CHARSET "UTF8"
#define CLIENT_ENCODING "client_encoding"
|
1fe399 | 2008-07-16 | Peter Bortas | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
f39097 | 2009-02-12 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
9a3d00 | 2011-01-09 | Henrik Grubbström (Grubba) | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
23914b | 2012-04-02 | Stephen R. van den Berg | |
|
bbf653 | 2012-04-13 | Stephen R. van den Berg | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
dc97bc | 2012-04-06 | Stephen R. van den Berg | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
1824a0 | 2009-04-10 | Stephen R. van den Berg | |
|
9a3d00 | 2011-01-09 | Henrik Grubbström (Grubba) | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
9a3d00 | 2011-01-09 | Henrik Grubbström (Grubba) | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
39fe7f | 2008-07-26 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
11b13b | 2014-08-16 | Martin Nilsson | | protected void create(void|string host, void|string database,
void|string user, void|string pass,
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | void|mapping(string:mixed) options) {
|
8e06a3 | 2014-09-30 | Martin Nilsson | | this::pass = pass;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(pass) {
|
334f37 | 2008-08-12 | Stephen R. van den Berg | | String.secure(pass);
|
11b13b | 2014-08-16 | Martin Nilsson | | pass = "CENSORED";
}
|
8e06a3 | 2014-09-30 | Martin Nilsson | | this::user = user;
this::database = database;
this::options = options || ([]);
|
11b13b | 2014-08-16 | Martin Nilsson | |
if(!host) host = PGSQL_DEFAULT_HOST;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(has_value(host,":") && sscanf(host,"%s:%d",host,_port)!=2)
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | ERROR("Error in parsing the hostname argument\n");
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | this::_host = host;
|
11b13b | 2014-08-16 | Martin Nilsson | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(!_port)
_port = PGSQL_DEFAULT_PORT;
.pgsql_util.register_backend();
waitforauth=Thread.Mutex();
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | reconnect();
}
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
f28c0d | 2008-08-01 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
be0739 | 2009-02-01 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | string error(void|int clear) {
throwdelayederror(this);
|
11b13b | 2014-08-16 | Martin Nilsson | | string s=lastmessage*"\n";
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | if(clear)
|
be0739 | 2009-02-01 | Stephen R. van den Berg | | lastmessage=({});
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | | warningscollected=0;
|
f11ef7 | 2009-02-01 | Stephen R. van den Berg | | return sizeof(s) && s;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
f28c0d | 2008-08-01 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | string host_info() {
|
11b13b | 2014-08-16 | Martin Nilsson | | return sprintf("fd:%d TCP/IP %s:%d PID %d",
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | c?c->socket->query_fd():-1,_host,_port,backendpid);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
6b4ea8 | 2012-04-10 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | int is_open() {
catch {
return c->socket->query_fd()>=0;
};
return 0;
|
6b4ea8 | 2012-04-10 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | |
|
6b4ea8 | 2012-04-10 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | int ping() {
return is_open() && !catch(c->start()->sendcmd(flushsend))
? !!reconnected : -1;
|
6b4ea8 | 2012-04-10 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | final protected object getsocket(void|int nossl) {
return .pgsql_util.PGassist(this,qportals,(int)nossl);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | void cancelquery() {
qstate=cancelpending;
PD("CancelRequest\n");
object lcon=getsocket(1);
lcon->add_int32(16)->add_int32(PG_PROTOCOL(1234,5678))
->add_int32(backendpid)->add(cancelsecret)->sendcmd(flushsend);
lcon->close();
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
9a3d00 | 2011-01-09 | Henrik Grubbström (Grubba) | |
|
26c0ad | 2009-02-28 | Stephen R. van den Berg | |
|
d6f86e | 2008-08-20 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
d6f86e | 2008-08-20 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | void set_charset(string charset) {
|
11b13b | 2014-08-16 | Martin Nilsson | | big_query(sprintf("SET CLIENT_ENCODING TO '%s'",quote(charset)));
|
d6f86e | 2008-08-20 | Stephen R. van den Berg | | }
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
d6f86e | 2008-08-20 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | string get_charset() {
|
11b13b | 2014-08-16 | Martin Nilsson | | return _runtimeparameter[CLIENT_ENCODING];
|
d6f86e | 2008-08-20 | Stephen R. van den Berg | | }
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
9a3d00 | 2011-01-09 | Henrik Grubbström (Grubba) | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
1824a0 | 2009-04-10 | Stephen R. van den Berg | |
|
9a3d00 | 2011-01-09 | Henrik Grubbström (Grubba) | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
cbe276 | 2008-08-01 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
e6d620 | 2012-04-16 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cbe276 | 2008-08-01 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | mapping(string:string) getruntimeparameters() {
|
11b13b | 2014-08-16 | Martin Nilsson | | return _runtimeparameter+([]);
|
cbe276 | 2008-08-01 | Stephen R. van den Berg | | }
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | #ifdef PG_STATS
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | #endif
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | #ifdef PG_STATS
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | #endif
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | mapping(string:mixed) getstatistics() {
|
11b13b | 2014-08-16 | Martin Nilsson | | mapping(string:mixed) stats=([
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | | "warnings_dropped":warningsdropcount,
"used_prepared_statements":prepstmtused,
"current_prepared_statements":sizeof(prepareds),
"current_prepared_statement_hits":totalhits,
"prepared_statement_count":pstmtcount,
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | #ifdef PG_STATS
"skipped_describe_count":skippeddescribe,
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | | "portals_opened_count":portalsopened,
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | #endif
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | | "messages_received":_msgsreceived,
"bytes_received":_bytesreceived,
"reconnect_count":reconnected,
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | "portals_in_flight":_portalsinflight,
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | | ]);
return stats;
}
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | int setcachedepth(void|int newdepth) {
|
11b13b | 2014-08-16 | Martin Nilsson | | int olddepth=cachedepth;
|
65340d | 2014-08-15 | Martin Nilsson | | if(!undefinedp(newdepth) && newdepth>=0)
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | cachedepth=newdepth;
return olddepth;
}
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | int settimeout(void|int newtimeout) {
|
11b13b | 2014-08-16 | Martin Nilsson | | int oldtimeout=timeout;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(!undefinedp(newtimeout) && newtimeout>0) {
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | timeout=newtimeout;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(c)
c->timeout=timeout;
}
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | return oldtimeout;
}
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | int setportalbuffersize(void|int newportalbuffersize) {
|
11b13b | 2014-08-16 | Martin Nilsson | | int oldportalbuffersize=portalbuffersize;
|
65340d | 2014-08-15 | Martin Nilsson | | if(!undefinedp(newportalbuffersize) && newportalbuffersize>0)
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | portalbuffersize=newportalbuffersize;
return oldportalbuffersize;
}
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | int setfetchlimit(void|int newfetchlimit) {
int oldfetchlimit=fetchlimit;
|
65340d | 2014-08-15 | Martin Nilsson | | if(!undefinedp(newfetchlimit) && newfetchlimit>=0)
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | fetchlimit=newfetchlimit;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | return oldfetchlimit;
}
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | final protected string glob2reg(string glob) {
|
11b13b | 2014-08-16 | Martin Nilsson | | if(!glob||!sizeof(glob))
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | return "%";
return replace(glob,({"*","?","\\","%","_"}),({"%","_","\\\\","\\%","\\_"}));
}
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | final protected string a2nls(array(string) msg) {
|
11b13b | 2014-08-16 | Martin Nilsson | | return msg*"\n"+"\n";
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | final protected string pinpointerror(void|string query,void|string offset) {
|
11b13b | 2014-08-16 | Martin Nilsson | | if(!query)
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | return "";
int k=(int)offset;
if(k<=0)
return MARKSTART+query+MARKEND;
return MARKSTART+(k>1?query[..k-2]:"")+MARKERROR+query[k-1..]+MARKEND;
}
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | protected void reconnect_cb() {
PD("%O\n",_runtimeparameter);
if(qstate==reconnectforce) {
lastmessage+=
({sprintf("Reconnected to database %s",host_info())});
runcallback(backendpid,"_reconnect","");
}
}
protected void processrowdescription(object portal) {
mapping(string:mixed) tp=portal._tprepared;
if(!tp || !tp.datarowdesc)
Thread.Thread(dodatarows,portal);
if(tp)
tp.datarowdesc=portal._datarowdesc;
}
protected array(string) showbindings(object portal) {
array(string) msgs=({});
array from;
if(portal && (from = portal._params)) {
array to,paramValues;
[from,to,paramValues] = from;
if(sizeof(paramValues)) {
string val;
int i;
string fmt=sprintf("%%%ds %%3s %%.61s",max(@map(from,sizeof)));
foreach(paramValues;i;val)
msgs+=({sprintf(fmt,from[i],to[i],sprintf("%O",val))});
|
bac80c | 2010-02-15 | Stephen R. van den Berg | | }
}
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | return msgs;
|
bac80c | 2010-02-15 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | protected void preplastmessage(mapping(string:string) msgresponse) {
lastmessage=({
sprintf("%s %s:%s %s\n (%s:%s:%s)",
msgresponse.S,msgresponse.C,msgresponse.P||"",
msgresponse.M,msgresponse.F||"",msgresponse.R||"",
msgresponse.L||"")});
}
protected void storetiming(object portal) {
mapping(string:mixed) tp=portal._tprepared;
tp.trun=gethrtime()-tp.trunstart;
m_delete(tp,"trunstart");
portal._tprepared = UNDEFINED;
}
final void _processloop(object ci) {
int die=0,terminating=0;
.pgsql_util.pgsql_result portal;
mixed err;
|
11b13b | 2014-08-16 | Martin Nilsson | | {
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | object plugbuffer=Stdio.Buffer()->add_int32(PG_PROTOCOL(3,0));
if(user)
plugbuffer->add("user\0")->add(user)->add_int8(0);
if(database)
plugbuffer->add("database\0")->add(database)->add_int8(0);
options->reconnect=undefinedp(options->reconnect) || options->reconnect;
foreach(options
-(<"use_ssl","force_ssl","cache_autoprepared_statements","reconnect",
"text_query","is_superuser","server_encoding","server_version",
"integer_datetimes","session_authorization">);
string name;mixed value)
plugbuffer->add(name)->add_int8(0)->add((string)value)->add_int8(0);
plugbuffer->add_int8(0);
PD("%O\n",(string)plugbuffer);
ci->start()->add_hstring(plugbuffer,4,4)->sendcmd(flushsend);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | cancelsecret=0;
PD("Processloop\n");
#ifdef PG_DEBUG
string datarowdebug;
int datarowdebugcount;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | #endif
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | for(;;) {
err=catch {
#ifdef PG_DEBUG
if(!portal && datarowdebug) {
PD("%s rows %d\n",datarowdebug,datarowdebugcount);
datarowdebug=0; datarowdebugcount=0;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | #endif
int msgtype=ci->read_int8();
if(!portal) {
portal=qportals->try_read();
if(portal)
PD("<%O %d %c switch portal ===================\n",
portal._portalname,++ci->queueinidx,msgtype);
}
if(qstate==cancelpending)
qstate=canceled,sendclose();
int msglen=ci->read_int32();
_msgsreceived++;
_bytesreceived+=1+msglen;
enum errortype {
noerror=0,
protocolerror,
protocolunsupported
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | };
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | errortype errtype=noerror;
switch(msgtype) {
array(mapping) getcols() {
int bintext=ci->read_int8();
int cols=ci->read_int16();
#ifdef PG_DEBUG
array a;
msglen-=4+1+2+2*cols;
foreach(a=allocate(cols,([]));;mapping m)
m.type=ci->read_int16();
#else
ci->consume(cols<<1);
#endif // Discard column info, and make it line oriented
return ({(["type":bintext?BYTEAOID:TEXTOID,"name":"line"])});
};
array(string) reads() {
#ifdef PG_DEBUG
if(msglen<1)
errtype=protocolerror;
#endif
array ret=({}),aw=({0});
do {
string w=ci->read_cstring();
msglen-=sizeof(w)+1; aw[0]=w; ret+=aw;
} while(msglen);
return ret;
};
mapping(string:string) getresponse() {
mapping(string:string) msgresponse=([]);
msglen-=4;
foreach(reads();;string f)
if(sizeof(f))
msgresponse[f[..0]]=f[1..];
PD("%O\n",msgresponse);
return msgresponse;
};
case 'R': {
PD("<Authentication ");
string sendpass;
int authtype;
msglen-=4+4;
switch(authtype=ci->read_int32()) {
case 0:
PD("Ok\n");
.pgsql_util.local_backend->remove_call_out(reconnect);
ci->gottimeout=gottimeout;
ci->timeout=timeout;
reconnectdelay=0;
cancelsecret="";
break;
case 2:
PD("KerberosV5\n");
errtype=protocolunsupported;
break;
case 3:
PD("ClearTextPassword\n");
sendpass=pass;
break;
case 4:
PD("CryptPassword\n");
errtype=protocolunsupported;
break;
case 5:
PD("MD5Password\n");
#ifdef PG_DEBUG
if(msglen<4)
errtype=protocolerror;
#endif
#define md5hex(x) String.string2hex(Crypto.MD5.hash(x))
sendpass=md5hex(pass+user);
sendpass="md5"+md5hex(sendpass+ci->read(msglen));
#ifdef PG_DEBUG
msglen=0;
#endif
break;
case 6:
PD("SCMCredential\n");
errtype=protocolunsupported;
break;
case 7:
PD("GSS\n");
errtype=protocolunsupported;
break;
case 9:
PD("SSPI\n");
errtype=protocolunsupported;
break;
case 8:
PD("GSSContinue\n");
errtype=protocolunsupported;
#ifdef PG_DEBUG
if(msglen<1)
errtype=protocolerror;
#endif
cancelsecret=ci->read(msglen);
#ifdef PG_DEBUG
msglen=0;
#endif
break;
default:
PD("Unknown Authentication Method %c\n",authtype);
errtype=protocolunsupported;
break;
}
switch(errtype) {
case noerror:
if(cancelsecret!="")
ci->start()->add_int8('p')->add_hstring(sendpass,4,5)
->add_int8(0)->sendcmd(flushsend);
break;
default:
case protocolunsupported:
ERROR("Unsupported authenticationmethod %c\n",authtype);
break;
|
c8942c | 2009-04-10 | Stephen R. van den Berg | | }
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | }
case 'K':
msglen-=4+4;backendpid=ci->read_int32();
cancelsecret=ci->read(msglen);
PD("<BackendKeyData %O\n",cancelsecret);
#ifdef PG_DEBUG
msglen=0;
#endif
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | case 'S': {
PD("<ParameterStatus ");
msglen-=4;
array(string) ts=reads();
#ifdef PG_DEBUG
if(sizeof(ts)==2) {
#endif
_runtimeparameter[ts[0]]=ts[1];
PD("%O=%O\n",ts[0],ts[1]);
#ifdef PG_DEBUG
} else
errtype=protocolerror;
#endif
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | }
case '3':
PD("<CloseComplete\n");
#ifdef PG_DEBUG
msglen-=4;
#endif
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | case 'Z':
#ifdef PG_DEBUG
msglen-=4+1;
#endif
backendstatus=ci->read_int8();
PD("<ReadyForQuery %c\n",backendstatus);
if(readyforquery_cb)
readyforquery_cb(),readyforquery_cb=0;
qstate=queryidle;
if(waitforauthready) {
Thread.MutexKey lock=waitforauth->lock();
waitforauthready->broadcast();
waitforauthready=0;
lock=0;
}
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | case '1':
PD("<ParseComplete\n");
#ifdef PG_DEBUG
msglen-=4;
#endif
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | case 't': {
array a;
int cols=ci->read_int16();
PD("<%O ParameterDescription %d values\n",portal._query,cols);
#ifdef PG_DEBUG
msglen-=4+2+4*cols;
#endif
foreach(a=allocate(cols);int i;)
a[i]=ci->read_int32();
#ifdef PG_DEBUGMORE
PD("%O\n",a);
#endif
if(portal._tprepared)
portal._tprepared.datatypeoid=a;
preparebind(portal);
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | }
case 'T': {
array a;
#ifdef PG_DEBUG
int cols=ci->read_int16();
PD("<RowDescription %d columns %O\n",cols,portal._query);
msglen-=4+2;
foreach(a=allocate(cols);int i;) {
#else
foreach(a=allocate(ci->read_int16());int i;) {
#endif
string s=ci->read_cstring();
mapping(string:mixed) res=(["name":s]);
#ifdef PG_DEBUG
msglen-=sizeof(s)+1+4+2+4+2+4+2;
res.tableoid=ci->read_int32()||UNDEFINED;
res.tablecolattr=ci->read_int16()||UNDEFINED;
#else
ci->consume(6);
#endif
res.type=ci->read_int32();
#ifdef PG_DEBUG
{
int len=ci->read_sint(2);
res.length=len>=0?len:"variable";
}
res.atttypmod=ci->read_int32();
res.formatcode=ci->read_int16();
#else
ci->consume(8);
#endif
a[i]=res;
}
#ifdef PG_DEBUGMORE
PD("%O\n",a);
#endif
portal._datarowdesc=a;
processrowdescription(portal);
portal=0;
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | }
case 'n': {
#ifdef PG_DEBUG
msglen-=4;
#endif
PD("<NoData %O\n",portal._query);
portal._datarowdesc=({});
portal._fetchlimit=0;
processrowdescription(portal);
portal=0;
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | }
case 'H':
portal._datarowdesc=getcols();
PD("<CopyOutResponse %d %O\n",
sizeof(portal._datarowdesc),portal._query);
processrowdescription(portal);
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | case '2': {
mapping tp;
#ifdef PG_DEBUG
msglen-=4;
#endif
PD("<%O BindComplete\n",portal._portalname);
if(tp=portal._tprepared) {
int tend=gethrtime();
int tstart=tp.trun;
if(tend==tstart)
m_delete(prepareds,portal._query);
else {
tp.hits++;
totalhits++;
if(!tp.preparedname) {
if(sizeof(portal._preparedname))
tp.preparedname=portal._preparedname;
tstart=tend-tstart;
if(!tp.tparse || tp.tparse>tstart)
tp.tparse=tstart;
}
tp.trunstart=tend;
}
}
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
}
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | case 'D': {
msglen-=4;
string serror;
if(portal._tprepared)
storetiming(portal);
#ifdef USEPGsql
ci->decodedatarow(msglen);msglen=0;
#else
array a, datarowdesc;
portal._bytesreceived+=msglen;
datarowdesc=portal._datarowdesc;
int cols=ci->read_int16();
#ifdef PG_DEBUG
|
cd7f23 | 2014-03-01 | Martin Nilsson | | #ifdef PG_DEBUGMORE
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | PD("<%O DataRow %d cols %d bytes\n",portal._portalname,cols,msglen);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | #endif
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | datarowdebugcount++;
if(!datarowdebug)
datarowdebug=sprintf(
"<%O DataRow %d cols %d bytes",portal._portalname,cols,msglen);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | #endif
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | int atext = portal._alltext;
int forcetext = portal._forcetext;
string cenc=_runtimeparameter[CLIENT_ENCODING];
a=allocate(cols,UNDEFINED);
msglen-=2+4*cols;
foreach(datarowdesc;int i;mapping m) {
int collen=ci->read_sint(4);
if(collen>0) {
msglen-=collen;
mixed value;
switch(int typ=m.type) {
case FLOAT4OID:
|
dc97bc | 2012-04-06 | Stephen R. van den Berg | | #if SIZEOF_FLOAT>=8
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | case FLOAT8OID:
|
7ac2f1 | 2008-07-27 | Stephen R. van den Berg | | #endif
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(!atext) {
value=(float)ci->read(collen);
break;
}
default:value=ci->read(collen);
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | case CHAROID:
value=atext?ci->read(1):ci->read_int8();
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | case BOOLOID:value=ci->read_int8();
switch(value) {
case 'f':value=0;
break;
case 't':value=1;
|
11b13b | 2014-08-16 | Martin Nilsson | | }
if(atext)
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | value=value?"t":"f";
break;
case TEXTOID:
case BPCHAROID:
case VARCHAROID:
value=ci->read(collen);
if(cenc==UTF8CHARSET && catch(value=utf8_to_string(value))
&& !serror)
serror=SERROR("%O contains non-%s characters\n",
value,UTF8CHARSET);
break;
case INT8OID:case INT2OID:
case OIDOID:case INT4OID:
if(forcetext) {
value=ci->read(collen);
if(!atext)
value=(int)value;
} else {
switch(typ) {
case INT8OID:value=ci->read_sint(8);
break;
case INT2OID:value=ci->read_sint(2);
break;
case OIDOID:
case INT4OID:value=ci->read_sint(4);
}
if(atext)
value=(string)value;
}
|
11b13b | 2014-08-16 | Martin Nilsson | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | a[i]=value;
} else if(!collen)
a[i]="";
|
11b13b | 2014-08-16 | Martin Nilsson | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | portal._inflight--;
portal._datarows->write(a);
if(serror)
ERROR(serror);
|
11b13b | 2014-08-16 | Martin Nilsson | | #endif // USEPGsql
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | portal->_processdataready(fetchlimit);
break;
}
case 's':
PD("<%O PortalSuspended\n",portal._portalname);
#if !STREAMEXECUTES
portal->_sendexecute(portal._fetchlimit);
#endif
#ifdef PG_DEBUG
msglen-=4;
#endif
portal=0;
break;
case 'C': {
msglen-=4;
#ifdef PG_DEBUG
if(msglen<1)
errtype=protocolerror;
#endif
string s=ci->read(msglen-1);
if(portal._tprepared)
storetiming(portal);
PD("<%O CommandComplete %O\n",portal._portalname,s);
if(!portal._statuscmdcomplete)
portal._statuscmdcomplete=s;
#ifdef PG_DEBUG
if(ci->read_int8())
errtype=protocolerror;
msglen=0;
#else
ci->consume(1);
#endif
portal->_releasesession();
portal=0;
break;
}
case 'I':
PD("<EmptyQueryResponse %O\n",portal._portalname);
#ifdef PG_DEBUG
msglen-=4;
#endif
portal->_releasesession();
portal=0;
break;
case 'd':
PD("<%O CopyData\n",portal._portalname);
if(portal._tprepared)
storetiming(portal);
msglen-=4;
#ifdef PG_DEBUG
if(msglen<0)
errtype=protocolerror;
#endif
portal._bytesreceived+=msglen;
portal._datarows->write(({ci->read(msglen)}));
#ifdef PG_DEBUG
msglen=0;
#endif
portal->_processdataready(fetchlimit);
break;
case 'G':
portal._datarowdesc=getcols();
PD("<%O CopyInResponse %d columns\n",
portal._portalname,sizeof(portal._datarowdesc));
portal._state=copyinprogress;
|
11b13b | 2014-08-16 | Martin Nilsson | | {
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | Thread.MutexKey resultlock=portal._resultmux->lock();
portal._newresult.signal();
resultlock=0;
|
11b13b | 2014-08-16 | Martin Nilsson | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | break;
case 'c':
#ifdef PG_DEBUG
PD("<%O CopyDone\n",portal._portalname);
msglen-=4;
#endif
portal=0;
break;
case 'E': {
if(portal)
portal->_releasesession();
PD("<%O ErrorResponse %O\n",
portal&&portal._portalname,portal&&portal._query);
mapping(string:string) msgresponse;
msgresponse=getresponse();
|
11b13b | 2014-08-16 | Martin Nilsson | | warningsdropcount+=warningscollected;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | warningscollected=0;
switch(msgresponse.C) {
case "P0001":
lastmessage=({sprintf("%s: %s",msgresponse.S,msgresponse.M)});
USERERROR(a2nls(lastmessage
+({pinpointerror(portal._query,msgresponse.P)})
+showbindings(portal)));
case "57P01":case "57P02":case "57P03":die=1;
preplastmessage(msgresponse);
PD(a2nls(lastmessage));USERERROR(a2nls(lastmessage));
case "08P01":case "42P05":
errtype=protocolerror;
case "XX000":case "42883":case "42P01":
invalidatecache=1;
default:
preplastmessage(msgresponse);
if(msgresponse.D)
lastmessage+=({msgresponse.D});
if(msgresponse.H)
lastmessage+=({msgresponse.H});
lastmessage+=({
pinpointerror(portal&&portal._query,msgresponse.P)+
pinpointerror(msgresponse.q,msgresponse.p)});
if(msgresponse.W)
lastmessage+=({msgresponse.W});
lastmessage+=showbindings(portal);
switch(msgresponse.S) {
case "PANIC":werror(a2nls(lastmessage));
}
USERERROR(a2nls(lastmessage));
}
break;
}
case 'N': {
PD("<NoticeResponse\n");
mapping(string:string) msgresponse;
msgresponse=getresponse();
if(clearmessage) {
warningsdropcount+=warningscollected;
clearmessage=warningscollected=0;
lastmessage=({});
}
warningscollected++;
lastmessage=({sprintf("%s %s: %s",
msgresponse.S,msgresponse.C,msgresponse.M)});
break;
}
case 'A': {
PD("<NotificationResponse\n");
|
11b13b | 2014-08-16 | Martin Nilsson | | msglen-=4+4;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | int pid=ci->read_int32();
|
11b13b | 2014-08-16 | Martin Nilsson | | string condition,extrainfo=UNDEFINED;
{
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | array(string) ts=reads();
switch(sizeof(ts)) {
#if PG_DEBUG
case 0:
errtype=protocolerror;
break;
default:
errtype=protocolerror;
#endif
case 2:
extrainfo=ts[1];
case 1:
condition=ts[0];
}
}
PD("%d %s\n%s\n",pid,condition,extrainfo);
runcallback(pid,condition,extrainfo);
break;
}
default:
if(msgtype!=-1) {
string s;
PD("Unknown message received %c\n",msgtype);
s=ci->read(msglen-=4);PD("%O\n",s);
#ifdef PG_DEBUG
msglen=0;
#endif
errtype=protocolunsupported;
} else {
if(!waitforauthready)
die=1;
lastmessage+=({
sprintf("Connection lost to database %s@%s:%d/%s %d\n",
user,_host,_port,database,backendpid)});
USERERROR(a2nls(lastmessage));
}
break;
|
11b13b | 2014-08-16 | Martin Nilsson | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | #ifdef PG_DEBUG
if(msglen)
errtype=protocolerror;
#endif
|
11b13b | 2014-08-16 | Martin Nilsson | | {
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | string msg;
switch(errtype) {
case protocolunsupported:
msg=sprintf("Unsupported servermessage received %c\n",msgtype);
break;
case protocolerror:
msg=sprintf("Protocol error with database %s",host_info());
break;
case noerror:
continue;
}
ERROR(a2nls(lastmessage+=({msg})));
|
11b13b | 2014-08-16 | Martin Nilsson | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | };
if(err==MAGICTERMINATE) {
ci->start()->add("X\0\0\0\4")->sendcmd(sendout);
terminating=1;
if(!sizeof(ci))
break;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(stringp(err)) {
object to=portal?portal:this;
if(!to._delayederror)
to._delayederror=err;
continue;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | break;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | _delayederror=err;
if(!ci->close() && !terminating && options.reconnect)
_connectfail();
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | void close() {
|
11b13b | 2014-08-16 | Martin Nilsson | | cancelquery();
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(c)
c->sendterminate();
c=0;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | void destroy() {
|
11b13b | 2014-08-16 | Martin Nilsson | | close();
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | .pgsql_util.unregister_backend();
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | void _connectfail(void|mixed err) {
if(err)
_delayederror=err;
if(!err || reconnectdelay) {
int tdelay;
switch(tdelay=reconnectdelay) {
case 0:
reconnectdelay=RECONNECTDELAY;
break;
default:
if(options.reconnect!=-1)
return;
reconnectdelay=RECONNECTBACKOFF;
break;
}
Thread.MutexKey lock=waitforauth->lock();
if(!waitforauthready)
waitforauthready=Thread.Condition();
lock=0;
.pgsql_util.local_backend->call_out(reconnect,tdelay,1);
}
}
protected int reconnect(void|int force,void|object tt) {
if(!force) {
Thread.MutexKey lock=waitforauth->lock();
if(waitforauthready) {
lock=0;
return 0;
}
waitforauthready=Thread.Condition();
lock=0;
}
if(c) {
|
11b13b | 2014-08-16 | Martin Nilsson | | reconnected++;
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | | prepstmtused=0;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | if(!force)
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | c->sendterminate();
|
49dbce | 2011-10-03 | Henrik Grubbström (Grubba) | | else
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | c->close();
c=0;
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | | foreach(prepareds;;mapping tp)
m_delete(tp,"preparedname");
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(!options.reconnect)
return 0;
|
6d9aa5 | 2008-08-21 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | qportals=Thread.Queue();
if(!(c=getsocket())) {
string msg=sprintf("Couldn't connect to database on %s:%d",_host,_port);
if(force) {
|
11b13b | 2014-08-16 | Martin Nilsson | | if(!sizeof(lastmessage) || lastmessage[sizeof(lastmessage)-1]!=msg)
|
6b4ea8 | 2012-04-10 | Stephen R. van den Berg | | lastmessage+=({msg});
|
6d9aa5 | 2008-08-21 | Stephen R. van den Berg | | return 0;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | } else
|
be0739 | 2009-02-01 | Stephen R. van den Berg | | ERROR(msg+"\n");
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | _runtimeparameter=([]);
unnamedportalmux=Thread.Mutex();
unnamedstatement=Thread.Mutex();
qstate=force?reconnectforce:streconnect;
readyforquery_cb=reconnect_cb;
_portalsinflight=0;
|
53b379 | 2010-03-23 | Stephen R. van den Berg | | return 1;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
e7621f | 2009-02-02 | Stephen R. van den Berg | |
|
f28c0d | 2008-08-01 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | void reload() {
|
11b13b | 2014-08-16 | Martin Nilsson | | resync();
|
e7621f | 2009-02-02 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | protected void resync_cb() {
switch(backendstatus) {
case 'T':case 'E':
foreach(prepareds;;mapping tp) {
m_delete(tp,"datatypeoid");
m_delete(tp,"datarowdesc");
}
big_query("ROLLBACK");
big_query("RESET ALL");
big_query("CLOSE ALL");
big_query("DISCARD TEMP");
}
}
|
e7621f | 2009-02-02 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
e7621f | 2009-02-02 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | void resync(void|int|object portal) {
|
11b13b | 2014-08-16 | Martin Nilsson | | mixed err;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(!is_open()&&!reconnect())
ERROR(a2nls(lastmessage));
err = catch {
PD("Portalsinflight: %d\n",_portalsinflight);
readyforquery_cb=resync_cb;
c->start()->add(PGSYNC)->sendcmd(sendout);
return;
};
PD("%O\n",err);
if(!reconnect())
|
6b81f4 | 2012-04-10 | Stephen R. van den Berg | | ERROR(a2nls(lastmessage));
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | void select_db(string dbname) {
|
11b13b | 2014-08-16 | Martin Nilsson | | database=dbname;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | reconnect();
|
b133b0 | 2008-08-06 | Stephen R. van den Berg | | reconnected=0;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
b133b0 | 2008-08-06 | Stephen R. van den Berg | |
|
9a3d00 | 2011-01-09 | Henrik Grubbström (Grubba) | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
9a3d00 | 2011-01-09 | Henrik Grubbström (Grubba) | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
7ac2f1 | 2008-07-27 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
7ac2f1 | 2008-07-27 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
7ac2f1 | 2008-07-27 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
void set_notify_callback(string condition,
void|function(int,string,string,mixed ...:void) notify_cb,void|int selfnotify,
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | mixed ... args) {
|
11b13b | 2014-08-16 | Martin Nilsson | | if(!notify_cb)
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | m_delete(notifylist,condition);
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | else {
|
11b13b | 2014-08-16 | Martin Nilsson | | array old=notifylist[condition];
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | if(!old)
old=({notify_cb});
if(selfnotify||args)
old+=({selfnotify});
if(args)
old+=args;
notifylist[condition]=old;
}
}
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | final protected void runcallback(int pid,string condition,string extrainfo) {
|
11b13b | 2014-08-16 | Martin Nilsson | | array cb;
|
b133b0 | 2008-08-06 | Stephen R. van den Berg | | if((cb=notifylist[condition]||notifylist[""])
|
11b13b | 2014-08-16 | Martin Nilsson | | && (pid!=backendpid || sizeof(cb)>1 && cb[1]))
|
b133b0 | 2008-08-06 | Stephen R. van den Berg | | cb[0](pid,condition,extrainfo,@cb[2..]);
}
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | string quote(string s) {
string r=_runtimeparameter.standard_conforming_strings;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | if(r && r=="on")
return replace(s, "'", "''");
return replace(s, ({ "'", "\\" }), ({ "''", "\\\\" }) );
}
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | string quotebinary(string s) {
|
11b13b | 2014-08-16 | Martin Nilsson | | return replace(s, ({ "'", "\\", "\0" }), ({ "''", "\\\\", "\\000" }) );
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | | }
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | void create_db(string db) {
|
71fc54 | 2014-08-13 | Stephen R. van den Berg | | big_query(sprintf("CREATE DATABASE %s",db));
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | |
|
9a3d00 | 2011-01-09 | Henrik Grubbström (Grubba) | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | void drop_db(string db) {
|
71fc54 | 2014-08-13 | Stephen R. van den Berg | | big_query(sprintf("DROP DATABASE %s",db));
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
f28c0d | 2008-08-01 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | string server_info () {
return DRIVERNAME"/"+(_runtimeparameter.server_version||"unknown");
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | array(string) list_dbs (void|string glob) {
|
11b13b | 2014-08-16 | Martin Nilsson | | array row,ret=({});
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | | object res=big_query("SELECT d.datname "
|
11b13b | 2014-08-16 | Martin Nilsson | | "FROM pg_database d "
"WHERE d.datname ILIKE :glob "
"ORDER BY d.datname",
([":glob":glob2reg(glob)]));
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | | while(row=res->fetch_row())
ret+=({row[0]});
return ret;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | array(string) list_tables (void|string glob) {
|
11b13b | 2014-08-16 | Martin Nilsson | | array row,ret=({});
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | | object res=big_query(
"SELECT CASE WHEN 'public'=n.nspname THEN '' ELSE n.nspname||'.' END "
" ||c.relname AS name "
"FROM pg_catalog.pg_class c "
" LEFT JOIN pg_catalog.pg_namespace n ON n.oid=c.relnamespace "
"WHERE c.relkind IN ('r','v') AND n.nspname<>'pg_catalog' "
" AND n.nspname !~ '^pg_toast' AND pg_catalog.pg_table_is_visible(c.oid) "
" AND c.relname ILIKE :glob "
" ORDER BY 1",
([":glob":glob2reg(glob)]));
while(row=res->fetch_row())
ret+=({row[0]});
return ret;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | array(mapping(string:mixed)) list_fields(void|string table, void|string glob) {
|
11b13b | 2014-08-16 | Martin Nilsson | | array row, ret=({});
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | string schema=UNDEFINED;
sscanf(table||"*", "%s.%s", schema, table);
|
98a776 | 2009-02-22 | Stephen R. van den Berg | | object res = big_typed_query(
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | "SELECT a.attname, a.atttypid, t.typname, a.attlen, "
|
98a776 | 2009-02-22 | Stephen R. van den Berg | | " c.relhasindex, c.relhaspkey, CAST(c.reltuples AS BIGINT) AS reltuples, "
" (c.relpages "
" +COALESCE( "
" (SELECT SUM(tst.relpages) "
" FROM pg_catalog.pg_class tst "
" WHERE tst.relfilenode=c.reltoastrelid) "
" ,0) "
" )*8192::BIGINT AS datasize, "
" (COALESCE( "
" (SELECT SUM(pin.relpages) "
" FROM pg_catalog.pg_index pi "
" JOIN pg_catalog.pg_class pin ON pin.relfilenode=pi.indexrelid "
" WHERE pi.indrelid IN (c.relfilenode,c.reltoastrelid)) "
" ,0) "
" )*8192::BIGINT AS indexsize, "
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | " c.relisshared, t.typdefault, "
" n.nspname, c.relname, "
" CASE c.relkind "
" WHEN 'r' THEN 'table' "
" WHEN 'v' THEN 'view' "
" WHEN 'i' THEN 'index' "
" WHEN 'S' THEN 'sequence' "
" WHEN 's' THEN 'special' "
|
7ac2f1 | 2008-07-27 | Stephen R. van den Berg | | " WHEN 't' THEN 'toastable' "
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | " WHEN 'c' THEN 'composite' "
" ELSE c.relkind::TEXT END AS relkind, "
" r.rolname "
|
98a776 | 2009-02-22 | Stephen R. van den Berg | | "FROM pg_catalog.pg_class c "
" LEFT JOIN pg_catalog.pg_namespace n ON n.oid=c.relnamespace "
" JOIN pg_catalog.pg_roles r ON r.oid=c.relowner "
" JOIN pg_catalog.pg_attribute a ON c.oid=a.attrelid "
" JOIN pg_catalog.pg_type t ON a.atttypid=t.oid "
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | "WHERE c.relname ILIKE :table AND "
" (n.nspname ILIKE :schema OR "
" :schema IS NULL "
|
98a776 | 2009-02-22 | Stephen R. van den Berg | | " AND n.nspname<>'pg_catalog' AND n.nspname !~ '^pg_toast') "
|
2c228b | 2009-02-15 | Stephen R. van den Berg | | " AND a.attname ILIKE :glob "
" AND (a.attnum>0 OR '*'=:realglob) "
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | "ORDER BY n.nspname,c.relname,a.attnum,a.attname",
([":schema":glob2reg(schema),":table":glob2reg(table),
|
11b13b | 2014-08-16 | Martin Nilsson | | ":glob":glob2reg(glob),":realglob":glob]));
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
array colnames=res->fetch_fields();
|
11b13b | 2014-08-16 | Martin Nilsson | | {
mapping(string:string) renames=([
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | "attname":"name",
"nspname":"schema",
"relname":"table",
"rolname":"owner",
"typname":"type",
"attlen":"length",
"typdefault":"default",
"relisshared":"is_shared",
"atttypid":"typeoid",
"relkind":"kind",
"relhasindex":"has_index",
"relhaspkey":"has_primarykey",
"reltuples":"rowcount",
]);
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | foreach(colnames;int i;mapping m) {
string nf,field=m.name;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | if(nf=renames[field])
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | | field=nf;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | colnames[i]=field;
}
}
#define delifzero(m,field) if(!(m)[field]) m_delete(m,field)
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | while(row=res->fetch_row()) {
|
11b13b | 2014-08-16 | Martin Nilsson | | mapping m=mkmapping(colnames,row);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | delifzero(m,"is_shared");
delifzero(m,"has_index");
delifzero(m,"has_primarykey");
delifzero(m,"default");
ret+=({m});
}
return ret;
}
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | protected int oidformat(int oid) {
switch(oid) {
case BOOLOID:
case BYTEAOID:
case CHAROID:
case INT8OID:
case INT2OID:
case INT4OID:
case TEXTOID:
case OIDOID:
case XMLOID:
case MACADDROID:
case BPCHAROID:
case VARCHAROID:
case CTIDOID:
case UUIDOID:
return 1;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | | return 0;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | final protected void sendclose() {
|
cd7f23 | 2014-03-01 | Martin Nilsson | | #ifdef PG_DEBUGMORE
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | PD("Closetrace %O\n",backtrace());
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | #endif
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | object plugbuffer=c->start(1);
foreach(qportals->peek_array();;object portal)
portal->_closeportal(plugbuffer);
plugbuffer->sendcmd(sendout);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | protected void gottimeout() {
sendclose();cancelquery();
}
final protected string trbackendst(int c) {
switch(c) {
case 'I': return "idle";
case 'T': return "intransaction";
case 'E': return "infailedtransaction";
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
928713 | 2008-09-03 | Stephen R. van den Berg | | return "";
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | final string status_commit() {
|
11b13b | 2014-08-16 | Martin Nilsson | | return trbackendst(backendstatus);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | final protected void closestatement(object plugbuffer,string oldprep) {
if(oldprep) {
|
11b13b | 2014-08-16 | Martin Nilsson | | PD("Close statement %s\n",oldprep);
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | plugbuffer->add_int8('C')->add_hstring(({'S',oldprep,0}),4,4);
|
d1a5a4 | 2008-08-27 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | }
final void throwdelayederror(object parent) {
.pgsql_util.throwdelayederror(parent);
|
d1a5a4 | 2008-08-27 | Stephen R. van den Berg | | }
|
041296 | 2009-01-19 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
13d29c | 2009-04-16 | Henrik Grubbström (Grubba) | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
dc97bc | 2012-04-06 | Stephen R. van den Berg | |
|
842f4e | 2012-04-10 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
17b753 | 2008-07-30 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
dc97bc | 2012-04-06 | Stephen R. van den Berg | |
|
17b753 | 2008-07-30 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
dc97bc | 2012-04-06 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | |
|
17b753 | 2008-07-30 | Stephen R. van den Berg | |
|
a2014e | 2008-07-14 | Stephen R. van den Berg | |
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
b15672 | 2008-08-25 | Stephen R. van den Berg | | object big_query(string q,void|mapping(string|int:mixed) bindings,
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | void|int _alltyped) {
throwdelayederror(this);
|
11b13b | 2014-08-16 | Martin Nilsson | | string preparedname="";
|
80dbe8 | 2008-08-08 | Stephen R. van den Berg | | int forcecache=-1;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | int forcetext=options.text_query;
|
26c0ad | 2009-02-28 | Stephen R. van den Berg | | string cenc=_runtimeparameter[CLIENT_ENCODING];
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | switch(cenc) {
case UTF8CHARSET:
q=string_to_utf8(q);
break;
default:
if(String.width(q)>8)
ERROR("Don't know how to convert %O to %s encoding\n",q,cenc);
|
26c0ad | 2009-02-28 | Stephen R. van den Berg | | }
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | array(string|int) paramValues;
|
c8942c | 2009-04-10 | Stephen R. van den Berg | | array from;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(bindings) {
|
11b13b | 2014-08-16 | Martin Nilsson | | int pi=0,rep=0;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | paramValues=allocate(sizeof(bindings));
|
11e81e | 2009-02-13 | Stephen R. van den Berg | | from=allocate(sizeof(bindings));
|
c8942c | 2009-04-10 | Stephen R. van den Berg | | array(string) to=allocate(sizeof(bindings));
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | foreach(bindings; mixed name; mixed value) {
if(stringp(name)) {
|
11b13b | 2014-08-16 | Martin Nilsson | | if(name[0]!=':')
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | | name=":"+name;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(name[1]=='_') {
switch(name) {
case ":_cache":
forcecache=(int)value;
break;
case ":_text":
forcetext=(int)value;
break;
|
80dbe8 | 2008-08-08 | Stephen R. van den Berg | | }
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | | continue;
}
|
9b6a8b | 2009-01-12 | Stephen R. van den Berg | | if(!has_value(q,name))
|
565d98 | 2008-08-27 | Stephen R. van den Berg | | continue;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
from[rep]=name;
string rval;
|
26c0ad | 2009-02-28 | Stephen R. van den Berg | | if(multisetp(value))
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | | rval=indices(value)*",";
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | else {
|
11b13b | 2014-08-16 | Martin Nilsson | | paramValues[pi++]=value;
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | | rval=sprintf("$%d",pi);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
to[rep++]=rval;
}
if(rep--)
|
11e81e | 2009-02-13 | Stephen R. van den Berg | | q=replace(q,from=from[..rep],to=to[..rep]);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | paramValues= pi ? paramValues[..pi-1] : ({});
|
c8942c | 2009-04-10 | Stephen R. van den Berg | | from=({from,to,paramValues});
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | } else
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | paramValues = ({});
|
26c0ad | 2009-02-28 | Stephen R. van den Berg | | if(String.width(q)>8)
ERROR("Wide string literals in %O not supported\n",q);
|
8a4ac4 | 2009-01-24 | Stephen R. van den Berg | | if(has_value(q,"\0"))
ERROR("Querystring %O contains invalid literal nul-characters\n",q);
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | | mapping(string:mixed) tp;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(waitforauthready) {
Thread.MutexKey lock=waitforauth->lock();
catch(waitforauthready->wait(lock));
lock=0;
}
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | int tstart;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(forcetext) {
|
11b13b | 2014-08-16 | Martin Nilsson | | if(bindings)
|
dc97bc | 2012-04-06 | Stephen R. van den Berg | | q = .sql_util.emulate_bindings(q, bindings, this);
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | } else if(forcecache==1
|| forcecache!=0 && (sizeof(q)>=MINPREPARELENGTH || cachealways[q])) {
object plugbuffer=c->start();
if(tp=prepareds[q]) {
if(tp.preparedname)
prepstmtused++, preparedname=tp.preparedname;
else if((tstart=tp.trun)
&& tp.tparse*FACTORPLAN>=tstart
&& (undefinedp(options.cache_autoprepared_statements)
|| options.cache_autoprepared_statements))
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | preparedname=PREPSTMTPREFIX+(string)pstmtcount++;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | } else {
|
11b13b | 2014-08-16 | Martin Nilsson | | if(totalhits>=cachedepth)
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | foreach(prepareds;string ind;tp) {
int oldhits=tp.hits;
totalhits-=oldhits-(tp.hits=oldhits>>1);
if(oldhits<=1) {
closestatement(plugbuffer,tp.preparedname);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | m_delete(prepareds,ind);
}
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(forcecache!=1 && createprefix->match(q)) {
|
11b13b | 2014-08-16 | Martin Nilsson | | invalidatecache=1;
tp=UNDEFINED;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | } else
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | | prepareds[q]=tp=([]);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(invalidatecache) {
|
11b13b | 2014-08-16 | Martin Nilsson | | invalidatecache=0;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | foreach(prepareds;;mapping np) {
closestatement(plugbuffer,np.preparedname);
|
c0f2b7 | 2009-04-10 | Stephen R. van den Berg | | m_delete(np,"preparedname");
|
d1a5a4 | 2008-08-27 | Stephen R. van den Berg | | }
}
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | if(sizeof(plugbuffer)) {
PD("%O\n",(string)plugbuffer);
plugbuffer->sendcmd(flushsend);
} else
plugbuffer->sendcmd();
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | tstart=gethrtime();
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | } else
|
cb2623 | 2008-08-04 | Stephen R. van den Berg | | tp=UNDEFINED;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | object portal;
portal=.pgsql_util.pgsql_result(this,c,q,
portalbuffersize,_alltyped,from,forcetext);
portal._tprepared=tp;
qstate=inquery;
#ifdef PG_STATS
portalsopened++;
#endif
clearmessage=1;
object plugbuffer=c;
if(forcetext) {
portal._unnamedportalkey=unnamedportalmux->lock(1);
portal->_openportal();
plugbuffer->start()->add_int8('Q')->add_hstring(q,4,4+1)->add_int8(0)
->sendcmd(flushsend,portal);
PD("Simple query: %O\n",q);
} else {
object parsebuffer;
if(!sizeof(preparedname) || !tp || !tp.preparedname) {
if(!sizeof(preparedname))
preparedname=
(portal._unnamedstatementkey=unnamedstatement->trylock(1))
? "" : PTSTMTPREFIX+(string)ptstmtcount++;
PD("Parse statement %O=%O\n",preparedname,q);
parsebuffer=plugbuffer->start()->add_int8('P')
->add_hstring(({preparedname,0,q,"\0\0\0"}),4,4)->add(PGFLUSH);
}
if(!tp || !tp.datatypeoid) {
PD("Describe statement %O\n",preparedname);
(parsebuffer||plugbuffer->start())->add_int8('D')
->add_hstring(({'S',preparedname,0}),4,4)->sendcmd(flushsend,portal);
} else {
if(parsebuffer)
parsebuffer->sendcmd();
#ifdef PG_STATS
skippeddescribe++;
#endif
portal._datarowdesc=tp.datarowdesc;
}
portal._preparedname=preparedname;
if((portal._tprepared=tp) && tp.datatypeoid) {
mixed e=catch(preparebind(portal));
if(e && !portal._delayederror) {
if(!stringp(e))
throw(e);
portal._delayederror=e;
|
488ce7 | 2008-07-24 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | }
}
throwdelayederror(portal);
return portal;
}
protected void preparebind(object portal) {
array dtoid=portal._tprepared.datatypeoid;
array(string|int) paramValues=portal._params?portal._params[2]:({});
if(sizeof(dtoid)!=sizeof(paramValues))
SUSERERROR("Invalid number of bindings, expected %d, got %d\n",
sizeof(dtoid),sizeof(paramValues));
#ifdef PG_DEBUGMORE
PD("ParamValues to bind: %O\n",paramValues);
#endif
object plugbuffer=Stdio.Buffer();
plugbuffer->add(portal._portalname=
(portal._unnamedportalkey=unnamedportalmux->trylock(1))
? "" : PORTALPREFIX+(string)_pportalcount++ )->add_int8(0)
->add(portal._preparedname)->add_int8(0)->add_int16(sizeof(paramValues));
foreach(dtoid;;int textbin)
plugbuffer->add_int16(oidformat(textbin));
plugbuffer->add_int16(sizeof(paramValues));
string cenc=_runtimeparameter[CLIENT_ENCODING];
foreach(paramValues;int i;mixed value) {
if(undefinedp(value))
plugbuffer->add_int32(-1);
else if(stringp(value) && !sizeof(value)) {
int k=0;
switch(dtoid[i]) {
default:
k=-1;
case BYTEAOID:
case TEXTOID:
case XMLOID:
case BPCHAROID:
case VARCHAROID:;
}
plugbuffer->add_int32(k);
} else
switch(dtoid[i]) {
case TEXTOID:
case BPCHAROID:
case VARCHAROID: {
if(!value) {
plugbuffer->add_int32(-1);
break;
|
dc97bc | 2012-04-06 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | value=(string)value;
switch(cenc) {
case UTF8CHARSET:
value=string_to_utf8(value);
break;
default:
if(String.width(value)>8) {
SUSERERROR("Don't know how to convert %O to %s encoding\n",
value,cenc);
value="";
|
dc97bc | 2012-04-06 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | }
plugbuffer->add_hstring(value,4);
break;
}
default: {
if(!value) {
plugbuffer->add_int32(-1);
break;
}
value=(string)value;
if(String.width(value)>8)
if(dtoid[i]==BYTEAOID)
value=string_to_utf8(value);
else {
SUSERERROR("Wide string %O not supported for type OID %d\n",
value,dtoid[i]);
value="";
|
dc97bc | 2012-04-06 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | plugbuffer->add_hstring(value,4);
break;
}
case BOOLOID:plugbuffer->add_int32(1);
do {
int tval;
if(stringp(value))
tval=value[0];
else if(!intp(value)) {
value=!!value;
break;
} else
tval=value;
switch(tval) {
case 'o':case 'O':
catch {
tval=value[1];
value=tval=='n'||tval=='N';
};
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | default:
value=1;
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | case 0:case '0':case 'f':case 'F':case 'n':case 'N':
value=0;
break;
}
} while(0);
plugbuffer->add_int8(value);
break;
case CHAROID:
if(intp(value))
plugbuffer->add_hstring(value,4);
else {
value=(string)value;
switch(sizeof(value)) {
default:
SUSERERROR(
"\"char\" types must be 1 byte wide, got %O\n",value);
case 0:
plugbuffer->add_int32(-1);
|
11b13b | 2014-08-16 | Martin Nilsson | | break;
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | case 1:
plugbuffer->add_hstring(value[0],4);
|
dc97bc | 2012-04-06 | Stephen R. van den Berg | | }
}
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | break;
case INT8OID:
plugbuffer->add_int32(8)->add_int((int)value,8);
break;
case OIDOID:
case INT4OID:
plugbuffer->add_int32(4)->add_int32((int)value);
break;
case INT2OID:
plugbuffer->add_int32(2)->add_int16((int)value);
break;
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
}
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | portal._plugbuffer=plugbuffer;
if(portal._tprepared)
if(portal._tprepared.datarowdesc)
dodatarows(portal);
else if(dontcacheprefix->match(portal._query))
m_delete(prepareds,portal._query),portal._tprepared=0;
}
protected void dodatarows(object portal) {
object plugbuffer=portal._plugbuffer;
portal._plugbuffer=0;
|
11b13b | 2014-08-16 | Martin Nilsson | | {
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | array a;
plugbuffer->add_int16(sizeof(a=portal._datarowdesc));
foreach(a;;mapping col)
plugbuffer->add_int16(oidformat(col.type));
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | PD("Bind portal %O statement %O\n",portal._portalname,portal._preparedname);
portal._fetchlimit=fetchlimit;
portal->_openportal();
object bindbuffer=c->start(1);
portal._unnamedstatementkey=0;
bindbuffer->add_int8('B')->add_hstring(plugbuffer,4,4);
if(!portal._tprepared)
closestatement(bindbuffer,portal._preparedname);
portal->_sendexecute(fetchlimit
&& !(cachealways[portal._query]
|| sizeof(portal._query)>=MINPREPARELENGTH &&
execfetchlimit->match(portal._query))
&& FETCHLIMITLONGRUN,bindbuffer);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
f4c9d6 | 2009-02-15 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | object streaming_query(string q,void|mapping(string|int:mixed) bindings) {
|
11b13b | 2014-08-16 | Martin Nilsson | | return big_query(q,bindings);
|
a2014e | 2008-07-14 | Stephen R. van den Berg | | }
|
b15672 | 2008-08-25 | Stephen R. van den Berg | |
|
2c228b | 2009-02-15 | Stephen R. van den Berg | |
|
cff3a3 | 2014-09-12 | Stephen R. van den Berg | | object big_typed_query(string q,void|mapping(string|int:mixed) bindings) {
|
11b13b | 2014-08-16 | Martin Nilsson | | return big_query(q,bindings,1);
|
b15672 | 2008-08-25 | Stephen R. van den Berg | | }
|