/ Check-in [e13993cf]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:Better error message text when the schema is corrupted by a CREATE TABLE AS entry.
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | corrupt-schema
Files: files | file ages | folders
SHA3-256: e13993cf833423eec5f94082cee7213b2d97bcf40dddb2683cf5a8ebf50a33e3
User & Date: drh 2018-03-16 20:15:58
Context
2018-03-16
20:23
Detect databases whose schema is corrupted using a CREATE TABLE AS statement and issue an appropriate error message. check-in: d75e6765 user: drh tags: trunk
20:15
Better error message text when the schema is corrupted by a CREATE TABLE AS entry. Closed-Leaf check-in: e13993cf user: drh tags: corrupt-schema
19:10
Fix a parsing issue associated with a corrupt sqlite_master table. check-in: 5f779ff6 user: mistachkin tags: corrupt-schema
Changes
Hide Diffs Side-by-Side Diffs Ignore Whitespace Patch

Changes to src/build.c.

  1866   1866     if( pEnd==0 && pSelect==0 ){
  1867   1867       return;
  1868   1868     }
  1869   1869     assert( !db->mallocFailed );
  1870   1870     p = pParse->pNewTable;
  1871   1871     if( p==0 ) return;
  1872   1872   
  1873         -  assert( !db->init.busy || !pSelect );
  1874         -
  1875   1873     /* If the db->init.busy is 1 it means we are reading the SQL off the
  1876   1874     ** "sqlite_master" or "sqlite_temp_master" table on the disk.
  1877   1875     ** So do not write to the disk again.  Extract the root page number
  1878   1876     ** for the table from the db->init.newTnum field.  (The page number
  1879   1877     ** should have been put there by the sqliteOpenCb routine.)
  1880   1878     **
  1881   1879     ** If the root page number is 1, that means this is the sqlite_master
  1882   1880     ** table itself.  So mark it read-only.
  1883   1881     */
  1884   1882     if( db->init.busy ){
         1883  +    if( pSelect ){
         1884  +      sqlite3ErrorMsg(pParse, "");
         1885  +      return;
         1886  +    }
  1885   1887       p->tnum = db->init.newTnum;
  1886   1888       if( p->tnum==1 ) p->tabFlags |= TF_Readonly;
  1887   1889     }
  1888   1890   
  1889   1891     /* Special processing for WITHOUT ROWID Tables */
  1890   1892     if( tabOpts & TF_WithoutRowid ){
  1891   1893       if( (p->tabFlags & TF_Autoincrement) ){

Changes to src/parse.y.

   165    165   temp(A) ::= TEMP.  {A = 1;}
   166    166   %endif  SQLITE_OMIT_TEMPDB
   167    167   temp(A) ::= .      {A = 0;}
   168    168   create_table_args ::= LP columnlist conslist_opt(X) RP(E) table_options(F). {
   169    169     sqlite3EndTable(pParse,&X,&E,F,0);
   170    170   }
   171    171   create_table_args ::= AS select(S). {
   172         -  if( pParse->db->init.busy==0 ){
   173         -    sqlite3EndTable(pParse,0,0,0,S);
   174         -    sqlite3SelectDelete(pParse->db, S);
   175         -  }else{
   176         -    sqlite3SelectDelete(pParse->db, S);
   177         -    sqlite3ErrorMsg(pParse, "corrupt schema");
   178         -  }
          172  +  sqlite3EndTable(pParse,0,0,0,S);
          173  +  sqlite3SelectDelete(pParse->db, S);
   179    174   }
   180    175   %type table_options {int}
   181    176   table_options(A) ::= .    {A = 0;}
   182    177   table_options(A) ::= WITHOUT nm(X). {
   183    178     if( X.n==5 && sqlite3_strnicmp(X.z,"rowid",5)==0 ){
   184    179       A = TF_WithoutRowid | TF_NoVisibleRowid;
   185    180     }else{

Changes to src/prepare.c.

    25     25     const char *zExtra   /* Error information */
    26     26   ){
    27     27     sqlite3 *db = pData->db;
    28     28     if( !db->mallocFailed && (db->flags & SQLITE_WriteSchema)==0 ){
    29     29       char *z;
    30     30       if( zObj==0 ) zObj = "?";
    31     31       z = sqlite3MPrintf(db, "malformed database schema (%s)", zObj);
    32         -    if( zExtra ) z = sqlite3MPrintf(db, "%z - %s", z, zExtra);
           32  +    if( zExtra && zExtra[0] ) z = sqlite3MPrintf(db, "%z - %s", z, zExtra);
    33     33       sqlite3DbFree(db, *pData->pzErrMsg);
    34     34       *pData->pzErrMsg = z;
    35     35     }
    36     36     pData->rc = db->mallocFailed ? SQLITE_NOMEM_BKPT : SQLITE_CORRUPT_BKPT;
    37     37   }
    38     38   
    39     39   /*