pike.git / lib / modules / Sql.pmod / pgsql.pike

version» Context lines:

pike.git/lib/modules/Sql.pmod/pgsql.pike:92:   private int skippeddescribe; // Number of times we skipped Describe phase   private int portalsopened; // Number of portals opened   int _msgsreceived; // Number of protocol messages received   int _bytesreceived; // Number of bytes received   int _packetssent; // Number of packets sent   int _bytessent; // Number of bytes sent   private int warningsdropcount; // Number of uncollected warnings   private int prepstmtused; // Number of times prepared statements were used   private int warningscollected;   private int invalidatecache; + private int connectionclosed;      private string host, database, user, pass;   private int port;   private object createprefix    =Regexp("^[ \t\f\r\n]*[Cc][Rr][Ee][Aa][Tt][Ee][ \t\f\r\n]");   private object dontcacheprefix    =Regexp("^[ \t\f\r\n]*([Ff][Ee][Tt][Cc][Hh]|[Cc][Oo][Pp][Yy])[ \t\f\r\n]");   private object limitpostfix    =Regexp("[ \t\f\r\n][Ll][Ii][Mm][Ii][Tt][ \t\f\r\n]+[12][; \t\f\r\n]*$");   Thread.Mutex _querymutex;
pike.git/lib/modules/Sql.pmod/pgsql.pike:531:      final private string pinpointerror(void|string query,void|string offset)   { if(!query)    return "";    int k=(int)offset;    if(k<=0)    return MARKSTART+query+MARKEND;    return MARKSTART+(k>1?query[..k-2]:"")+MARKERROR+query[k-1..]+MARKEND;   }    + private void phasedreconnect() + { connectionclosed=1; +  if(!reconnect(1)) +  { sleep(RECONNECTDELAY); +  if(!reconnect(1)) +  { sleep(RECONNECTBACKOFF); +  reconnect(1); +  } +  } + } +    final int _decodemsg(void|state waitforstate)   {   #ifdef DEBUG    { array line;   #ifdef DEBUGMORE    line=backtrace();   #endif    PD("Waiting for state %O %O\n",waitforstate,line&&line[sizeof(line)-2]);    }   #endif
pike.git/lib/modules/Sql.pmod/pgsql.pike:882:    case 'G':PD("CopyInResponse\n");    getcols();    _mstate=copyinresponse;    break;    case 'c':PD("CopyDone\n");    msglen-=4;    break;    case 'E':PD("ErrorResponse\n");    { mapping(string:string) msgresponse;    msgresponse=getresponse(); +  void preplastmessage() +  { lastmessage=({sprintf("%s %s:%s %s\n (%s:%s:%s)", +  msgresponse->S,msgresponse->C,msgresponse->P||"",msgresponse->M, +  msgresponse->F||"",msgresponse->R||"",msgresponse->L||"")}); +  };    warningsdropcount+=warningscollected;    warningscollected=0;    switch(msgresponse->C)    { case "P0001":    lastmessage=({sprintf("%s: %s",msgresponse->S,msgresponse->M)});    USERERROR(a2nls(lastmessage    +({pinpointerror(_c.portal->_query,msgresponse->P)})    +showbindings())); -  +  case "57P01":case "57P02":case "57P03": +  preplastmessage();phasedreconnect(); +  PD(a2nls(lastmessage)); +  USERERROR(a2nls(lastmessage));    case "08P01":case "42P05":    errtype=protocolerror;    case "XX000":case "42883":case "42P01":    invalidatecache=1;    default: -  lastmessage=({sprintf("%s %s:%s %s\n (%s:%s:%s)", -  msgresponse->S,msgresponse->C,msgresponse->P||"",msgresponse->M, -  msgresponse->F||"",msgresponse->R||"",msgresponse->L||"")}); +  preplastmessage();    if(msgresponse->D)    lastmessage+=({msgresponse->D});    if(msgresponse->H)    lastmessage+=({msgresponse->H});    lastmessage+=({    pinpointerror(_c.portal&&_c.portal->_query,msgresponse->P)+    pinpointerror(msgresponse->q,msgresponse->p)});    if(msgresponse->W)    lastmessage+=({msgresponse->W});    lastmessage+=showbindings();
pike.git/lib/modules/Sql.pmod/pgsql.pike:953:    break;    }    default:    if(msgtype!=-1)    { PD("Unknown message received %c\n",msgtype);    msglen-=4;PD("%O\n",_c.getstring(msglen));msglen=0;    errtype=protocolunsupported;    }    else    { array(string) msg=lastmessage; -  if(!reconnect(1)) -  { sleep(RECONNECTDELAY); -  if(!reconnect(1)) -  { sleep(RECONNECTBACKOFF); -  reconnect(1); -  } -  } -  msg+=lastmessage; +  phasedreconnect();msg+=lastmessage;    string s=sizeof(msg)?a2nls(msg):"";    ERROR("%sConnection lost to database %s@%s:%d/%s %d\n",    s,user,host,port,database,backendpid);    }    break;    }    if(msglen)    errtype=protocolerror;    switch(errtype)    { case protocolunsupported:    ERROR("Unsupported servermessage received %c\n",msgtype);    break;    case protocolerror:    array(string) msg=lastmessage; -  lastmessage=({}); -  reconnect(1); -  msg+=lastmessage; +  lastmessage=({});phasedreconnect();msg+=lastmessage;    string s=sizeof(msg)?a2nls(msg):"";    ERROR("%sProtocol error with database %s\n",s,host_info());    break;    case noerror:    break;    }    if(zero_type(waitforstate))    break;    }    PD("Found state %O\n",_mstate);
pike.git/lib/modules/Sql.pmod/pgsql.pike:1699:    }    }    if(sizeof(plugbuf))    { _c.sendcmd(plugbuf,1); // close expireds    PD("%O\n",plugbuf);    }    tstart=gethrtime();    } // pgsql_result autoassigns to portal    else    tp=UNDEFINED; +  connectionclosed=0; +  for(;;) +  {    .pgsql_util.pgsql_result(this,q,_fetchlimit,portalbuffersize,_alltyped,from);    if(unnamedportalinuse)    portalname=PORTALPREFIX+(string)pportalcount++;    else    unnamedportalinuse++;    _c.portal->_portalname=portalname;    qstate=inquery;    portalsinflight++; portalsopened++;    clearmessage=1;    mixed err; -  if(err = catch +  if(!(err = catch    { if(!sizeof(preparedname) || !tp || !tp->preparedname)    { PD("Parse statement %s\n",preparedname);    // Even though the protocol doesn't require the Parse command to be    // followed by a flush, it makes a VERY noticeable difference in    // performance if it is omitted; seems like a flaw in the PostgreSQL    // server v8.3.3    _c.sendcmd(({"P",_c.plugint32(4+sizeof(preparedname)+1+sizeof(q)+1+2),    preparedname,"\0",q,"\0",_c.plugint16(0)}),3);    PD("Query: %O\n",q);    } // sends Parameter- and RowDescription for 'S'
pike.git/lib/modules/Sql.pmod/pgsql.pike:1903:    { if(sizeof(preparedname))    tp->preparedname=preparedname;    tstart=tend-tstart;    if(!tp->tparse || tp->tparse>tstart)    tp->tparse=tstart;    }    tp->trunstart=tend;    }    tprepared=tp;    } -  }) -  { PD("%O\n",err); +  })) +  break; +  PD("%O\n",err);    resync(1);    backendstatus=UNDEFINED; -  +  if(!connectionclosed)    throw(err); -  +  tp=UNDEFINED;    }    { object tportal=_c.portal; // Make copy, because it might dislodge    tportal->fetch_row(1); // upon initial fetch_row()    return tportal;    }   }      //! This is an alias for @[big_query()], since @[big_query()] already supports   //! streaming of multiple simultaneous queries through the same connection.   //!