List:MySQL and Perl« Previous MessageNext Message »
From:Ralf Neubauer Date:October 18 2011 4:13pm
Subject:DBD::mysql: no errstr under Windows
View as plain text  
Hi,

as you may have seen in https://rt.cpan.org/Public/Bug/Display.html?id=71047 or even in
http://bugs.activestate.com/show_bug.cgi?id=91026 there is no ->errstr or ->err on
the Windows platform, if ->execute failed.

In DBD::mysql 4.018 the code at the end of mysql_st_internal_execute() in dbdimp.c that
executed the statement and transferred the error codes looked like this:

if ((mysql_real_query(svsock, sbuf, slen))  &&
      (!mysql_db_reconnect(h)  ||
       (mysql_real_query(svsock, sbuf, slen))))
  {
    Safefree(salloc);
    do_error(h, mysql_errno(svsock), mysql_error(svsock), 
             mysql_sqlstate(svsock));
    if (DBIc_TRACE_LEVEL(imp_xxh) >= 2)
      PerlIO_printf(DBILOGFP, "IGNORING ERROR errno %d\n", errno);
    return -2;
  }
  Safefree(salloc);

In 4.020 it looks like this (Note that MYSQL_ASYNC is 0 on the Windows platform as defined
in dbdimp.h):

#if MYSQL_ASYNC
  if(async) {
    if((mysql_send_query(svsock, sbuf, slen)) &&
       (!mysql_db_reconnect(h) ||
        (mysql_send_query(svsock, sbuf, slen))))
    {
        rows = -2;
    } else {
        rows = 0;
    }
  } else {
#endif
      if ((mysql_real_query(svsock, sbuf, slen))  &&
          (!mysql_db_reconnect(h)  ||
           (mysql_real_query(svsock, sbuf, slen))))
      {
        rows = -2;
      } else {
          /** Store the result from the Query */
          *result= use_mysql_use_result ?
            mysql_use_result(svsock) : mysql_store_result(svsock);

          if (mysql_errno(svsock))
            do_error(h, mysql_errno(svsock), mysql_error(svsock)
                     ,mysql_sqlstate(svsock));

          if (!*result)
            rows= mysql_affected_rows(svsock);
          else
            rows= mysql_num_rows(*result);
      }
#if MYSQL_ASYNC
  }
  Safefree(salloc);

  if(rows == -2) {
    do_error(h, mysql_errno(svsock), mysql_error(svsock), 
             mysql_sqlstate(svsock));
    if (DBIc_TRACE_LEVEL(imp_xxh) >= 2)
      PerlIO_printf(DBILOGFP, "IGNORING ERROR errno %d\n", errno);
    rows = -2;
  }
#endif


Instead of directly calling do_error(), the error is marked by setting rows = -2. Whis is
just returned, if MYSQL_ACTIVE is not set, without calling do_error() before.
I suggest to move the final #endif to execute the if(rows == -2) {...} handler even if
MYSQL_ASYNC is 0. From the look of it, it may be useful to unconditionally the
Safefree(salloc) also.
And why is rows set to -2 if rows == -2?

Ralf

--
Ralf Neubauer
Wissenschaftliches Institut der AOK (WIdO)
Rosenthaler Straße 31
10178 Berlin
Tel: 030 34646-2583
Fax: 030 34646-2144
E-Mail: Ralf.Neubauer@stripped
Thread
DBD::mysql: no errstr under WindowsRalf Neubauer18 Oct