]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
Fix problems in ALTER TABLE that occur when column or table names are
authordrh <drh@noemail.net>
Tue, 15 May 2007 03:56:49 +0000 (03:56 +0000)
committerdrh <drh@noemail.net>
Tue, 15 May 2007 03:56:49 +0000 (03:56 +0000)
invalid UTF encodings. (CVS 4000)

FossilOrigin-Name: 9ff382f4584ff685a78b39f24424319709efb382

manifest
manifest.uuid
src/alter.c
src/build.c
src/test1.c
test/alter.test
test/fuzz2.test

index d4984993044a84a0161c03f05604477f55402c7f..2311f0bbfdc2484c00c382424f49de1e26b482e5 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Fix\sa\stypo\sin\sa\scomment.\s\sTicket\s#2359.\s(CVS\s3999)
-D 2007-05-15T02:45:19
+C Fix\sproblems\sin\sALTER\sTABLE\sthat\soccur\swhen\scolumn\sor\stable\snames\sare\ninvalid\sUTF\sencodings.\s(CVS\s4000)
+D 2007-05-15T03:56:49
 F Makefile.in 87b200ad9970907f76df734d29dff3d294c10935
 F Makefile.linux-gcc 2d8574d1ba75f129aba2019f0b959db380a90935
 F README 9c4e2d6706bdcc3efdd773ce752a8cdab4f90028
@@ -57,14 +57,14 @@ F sqlite.pc.in 30552343140c53304c2a658c080fbe810cd09ca2
 F sqlite3.1 6be1ad09113570e1fc8dcaff84c9b0b337db5ffc
 F sqlite3.def a96c1d0d39362b763d2ddba220a32da41a15c4b4
 F sqlite3.pc.in 985b9bf34192a549d7d370e0f0b6b34a4f61369a
-F src/alter.c ca8fc4a3c7359379598dc12589b65c32eb88defd
+F src/alter.c 357378a0c09b654d9ae3764e58ba1034da4552b5
 F src/analyze.c e8fcb1c35ace8418615eb18d9601f321ac86b2ec
 F src/attach.c ba628db0c2b6a362f036d017bf1196cdfe4ebb37
 F src/auth.c 5ea90bc93dfea46e9fe4bf531e14c7cd98219ecb
 F src/btree.c 0c2f9b06c90d7c59925c03153c9d47fd739c8ca5
 F src/btree.h 1d527bf61ed176f980c34999d5793a0fd45dcf8c
 F src/btreeInt.h cb3c0e9eb842d06079a62cdf3492c90c5db7ba75
-F src/build.c 8e744caf66d4411143985863108736887096d634
+F src/build.c a27a21a23fb08db0a9d6711e296f54b04fa25cee
 F src/callback.c 9c12535669a638f90a67e10440b99c7b93c0fbf4
 F src/complete.c 7d1a44be8f37de125fcafd3d3a018690b3799675
 F src/date.c 6049db7d5a8fdf2c677ff7d58fa31d4f6593c988
@@ -107,7 +107,7 @@ F src/sqlite3ext.h 7d0d363ea7327e817ef0dfe1b7eee1f171b72890
 F src/sqliteInt.h c31c9526bc602c3c71ddc45c548e987530826f11
 F src/table.c a8de75bcedf84d4060d804264b067ab3b1a3561d
 F src/tclsqlite.c f425c7583665ef78dd8397b2de0b8e0028e80ce2
-F src/test1.c 16938b7e76469abf957745743dd0287d5dee476d
+F src/test1.c 84c841e1088f743200b87581506e93f70344bd32
 F src/test2.c 24458b17ab2f3c90cbc1c8446bd7ffe69be62f88
 F src/test3.c 946ea9d1a8c928656e3c70f0a2fcb8e733a15e86
 F src/test4.c 8b784cd82de158a2317cb4ac4bc86f91ad315e25
@@ -145,7 +145,7 @@ F src/where.c f3920748cc650fc25ac916215500bdb90dee568e
 F tclinstaller.tcl 4356d9d94d2b5ed5e68f9f0c80c4df3048dd7617
 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2
 F test/all.test 93a40a7612b3c5e6efd1f5b98496a8b02a45cfdb
-F test/alter.test 0e69c016b5aacd4cc692e63115655c885bfe3c22
+F test/alter.test 1513354e75cad76180d2ac06a20665193210c0d7
 F test/alter2.test 50c3f554b8236d179d72511c0a4f23c5eb7f2af3
 F test/alter3.test a6eec8f454be9b6ce73d8d7dc711453675a10ce7
 F test/altermalloc.test 19323e0f452834044c27a54c6e78554d706de7ba
@@ -249,7 +249,7 @@ F test/fts2m.test 4b30142ead6f3ed076e880a2a464064c5ad58c51
 F test/fts2n.test a70357e72742681eaebfdbe9007b87ff3b771638
 F test/func.test bf30bac1c5ce10448ab739994268cf18f8b3fa30
 F test/fuzz.test f5c67c3bbf2031d6d1c08a546569831d53dc6452
-F test/fuzz2.test fdbea571808441c12c91e9cd038eb77b4692d42b
+F test/fuzz2.test f1866329c9d0869297fb47fd1b4f597d5b66ac97
 F test/hook.test 7e7645fd9a033f79cce8fdff151e32715e7ec50a
 F test/icu.test e6bfae7f625c88fd14df6f540fe835bdfc1e4329
 F test/in.test 369cb2aa1eab02296b4ec470732fe8c131260b1d
@@ -491,7 +491,7 @@ F www/tclsqlite.tcl bb0d1357328a42b1993d78573e587c6dcbc964b9
 F www/vdbe.tcl 87a31ace769f20d3627a64fa1fade7fed47b90d0
 F www/version3.tcl 890248cf7b70e60c383b0e84d77d5132b3ead42b
 F www/whentouse.tcl fc46eae081251c3c181bd79c5faef8195d7991a5
-P 5af49a57d4866be21c0206f34584bcc63adc1315
-R 93a3d51fc25837371e9b0e6fd514aa55
+P 1fbbc108a9e7ad1dc22c08ee990e2b6b949784eb
+R b8fe54c7bac8048083b2ee052aff15ca
 U drh
-Z 35fee69111bd42bfa0668ba9070de64e
+Z e8c0d1effc885ae48b4a6dcdd97879b1
index aa936a51d3c2cd797bb2c94fec8195417b63ccba..73ec0e36b2adab33ada5a339bdc4b77c826ca777 100644 (file)
@@ -1 +1 @@
-1fbbc108a9e7ad1dc22c08ee990e2b6b949784eb
\ No newline at end of file
+9ff382f4584ff685a78b39f24424319709efb382
\ No newline at end of file
index d6f930eee27c3ff6721019bc163cd15f0faa9ad4..7049674b26d935ad60599eb6e82f7f965a435142 100644 (file)
@@ -12,7 +12,7 @@
 ** This file contains C code routines that used to generate VDBE code
 ** that implements the ALTER TABLE command.
 **
-** $Id: alter.c,v 1.23 2007/05/08 12:37:46 danielk1977 Exp $
+** $Id: alter.c,v 1.24 2007/05/15 03:56:49 drh Exp $
 */
 #include "sqliteInt.h"
 #include <ctype.h>
@@ -273,6 +273,9 @@ void sqlite3AlterRenameTable(
   Table *pTab;              /* Table being renamed */
   char *zName = 0;          /* NULL-terminated version of pName */ 
   sqlite3 *db = pParse->db; /* Database connection */
+  int i;                    /* Loop counter */
+  int nTabName;             /* Number of UTF-8 characters in zTabName */
+  const char *zTabName;     /* Original name of the table */
   Vdbe *v;
 #ifndef SQLITE_OMIT_TRIGGER
   char *zWhere = 0;         /* Where clause to locate temp triggers */
@@ -334,6 +337,12 @@ void sqlite3AlterRenameTable(
   sqlite3BeginWriteOperation(pParse, 0, iDb);
   sqlite3ChangeCookie(db, v, iDb);
 
+  /* figure out how many UTF-8 characters are in zName */
+  zTabName = pTab->zName;
+  for(i=nTabName=0; zTabName[i]; i++){
+    if( (zTabName[i]&0xc0)!=0x80 ) nTabName++;
+  }
+
   /* Modify the sqlite_master table to use the new table name. */
   sqlite3NestedParse(pParse,
       "UPDATE %Q.%s SET "
@@ -348,7 +357,7 @@ void sqlite3AlterRenameTable(
           "name = CASE "
             "WHEN type='table' THEN %Q "
             "WHEN name LIKE 'sqlite_autoindex%%' AND type='index' THEN "
-              "'sqlite_autoindex_' || %Q || substr(name, %d+18,10) "
+             "'sqlite_autoindex_' || %Q || substr(name,%d+18,10) "
             "ELSE name END "
       "WHERE tbl_name=%Q AND "
           "(type='table' OR type='index' OR type='trigger');", 
@@ -356,7 +365,7 @@ void sqlite3AlterRenameTable(
 #ifndef SQLITE_OMIT_TRIGGER
       zName,
 #endif
-      zName, strlen(pTab->zName), pTab->zName
+      zName, nTabName, zTabName
   );
 
 #ifndef SQLITE_OMIT_AUTOINCREMENT
index 4d4a30e8030e5c9efa0f5c3fc81744f02b9cf72f..9f6cafd24a1c2cbaa29a7dd4ca2063c3ce3af435 100644 (file)
@@ -22,7 +22,7 @@
 **     COMMIT
 **     ROLLBACK
 **
-** $Id: build.c,v 1.430 2007/05/12 15:00:15 drh Exp $
+** $Id: build.c,v 1.431 2007/05/15 03:56:49 drh Exp $
 */
 #include "sqliteInt.h"
 #include <ctype.h>
@@ -1562,13 +1562,16 @@ void sqlite3EndTable(
 #ifndef SQLITE_OMIT_ALTERTABLE
     if( !p->pSelect ){
       const char *zName = (const char *)pParse->sNameToken.z;
-      int nName;
+      int nName, i, nUtfChar;
       assert( !pSelect && pCons && pEnd );
       if( pCons->z==0 ){
         pCons = pEnd;
       }
       nName = (const char *)pCons->z - zName;
-      p->addColOffset = 13 + sqlite3Utf8CharLen(zName, nName);
+      for(i=nUtfChar=0; i<nName; i++){
+        if( (zName[i]&0xc0)!=0x80 ) nUtfChar++;
+      }
+      p->addColOffset = 13 + nUtfChar;
     }
 #endif
   }
index 4f26a8990a989ebd475d3aede8d79d5efeab63a3..d2e5dccd92e661e98a0be3b80e7395f857db551e 100644 (file)
@@ -13,7 +13,7 @@
 ** is not included in the SQLite library.  It is used for automated
 ** testing of the SQLite library.
 **
-** $Id: test1.c,v 1.252 2007/05/08 20:37:39 drh Exp $
+** $Id: test1.c,v 1.253 2007/05/15 03:56:50 drh Exp $
 */
 #include "sqliteInt.h"
 #include "tcl.h"
@@ -338,6 +338,8 @@ static int test_exec(
   Tcl_DString str;
   int rc;
   char *zErr = 0;
+  char *zSql;
+  int i, j;
   char zBuf[30];
   if( argc!=3 ){
     Tcl_AppendResult(interp, "wrong # args: should be \"", argv[0], 
@@ -346,7 +348,18 @@ static int test_exec(
   }
   if( getDbPointer(interp, argv[1], &db) ) return TCL_ERROR;
   Tcl_DStringInit(&str);
-  rc = sqlite3_exec(db, argv[2], exec_printf_cb, &str, &zErr);
+  zSql = sqlite3_mprintf("%s", argv[2]);
+  for(i=j=0; zSql[i];){
+    if( zSql[i]=='%' ){
+      zSql[j++] = (testHexToInt(zSql[i+1])<<4) + testHexToInt(zSql[i+2]);
+      i += 3;
+    }else{
+      zSql[j++] = zSql[i++];
+    }
+  }
+  zSql[j] = 0;
+  rc = sqlite3_exec(db, zSql, exec_printf_cb, &str, &zErr);
+  sqlite3_free(zSql);
   sprintf(zBuf, "%d", rc);
   Tcl_AppendElement(interp, zBuf);
   Tcl_AppendElement(interp, rc==SQLITE_OK ? Tcl_DStringValue(&str) : zErr);
index 6dd56b7a679f3b7cbfdb8222efcba22ca69d282d..41234677dc3b2c198e4b2233253766ebdaf18c9a 100644 (file)
@@ -11,7 +11,7 @@
 # This file implements regression tests for SQLite library.  The
 # focus of this script is testing the ALTER TABLE statement.
 #
-# $Id: alter.test,v 1.21 2007/05/15 00:09:13 drh Exp $
+# $Id: alter.test,v 1.22 2007/05/15 03:56:50 drh Exp $
 #
 
 set testdir [file dirname $argv0]
@@ -97,6 +97,7 @@ do_test alter-1.2 {
 
 # Make some changes
 #
+integrity_check alter-1.3.0
 do_test alter-1.3 {
   execsql {
     ALTER TABLE [T1] RENAME to [-t1-];
@@ -665,12 +666,41 @@ ifcapable trigger {
   } {{}}
 }
 do_test alter-9.2 {
-    execsql {
+  execsql {
     SELECT SQLITE_RENAME_TABLE(0,0);
     SELECT SQLITE_RENAME_TABLE(10,20);
     SELECT SQLITE_RENAME_TABLE("foo", "foo");
   }
 } {{} {} {}}
 
+#------------------------------------------------------------------------
+# alter-10.X - Make sure ALTER TABLE works with multi-byte UTF-8 characters 
+# in the names.
+#
+do_test alter-10.1 {
+  execsql "CREATE TABLE xyz(x UNIQUE)"
+  execsql "ALTER TABLE xyz RENAME TO xyz\u1234abc"
+  execsql {SELECT name FROM sqlite_master WHERE name LIKE 'xyz%'}
+} [list xyz\u1234abc]
+do_test alter-10.2 {
+  execsql {SELECT name FROM sqlite_master WHERE name LIKE 'sqlite_autoindex%'}
+} [list sqlite_autoindex_xyz\u1234abc_1]
+do_test alter-10.3 {
+  execsql "ALTER TABLE xyz\u1234abc RENAME TO xyzabc"
+  execsql {SELECT name FROM sqlite_master WHERE name LIKE 'xyz%'}
+} [list xyzabc]
+do_test alter-10.4 {
+  execsql {SELECT name FROM sqlite_master WHERE name LIKE 'sqlite_autoindex%'}
+} [list sqlite_autoindex_xyzabc_1]
+
+do_test alter-11.1 {
+  sqlite3_exec db {CREATE TABLE t11(%c6%c6)}
+  execsql {
+    ALTER TABLE t11 ADD COLUMN abc;
+  }
+  catchsql {
+    ALTER TABLE t11 ADD COLUMN abc;
+  }
+} {1 {duplicate column name: abc}}
 
 finish_test
index 3c72c0d20c39da6d84f782eaac883c029ea300fb..7c35d73b5199116f91477efaecb0eb36a17fba9b 100644 (file)
@@ -12,7 +12,7 @@
 #
 # This file checks error recovery from malformed SQL strings.
 #
-# $Id: fuzz2.test,v 1.1 2007/05/11 00:20:08 drh Exp $
+# $Id: fuzz2.test,v 1.2 2007/05/15 03:56:50 drh Exp $
 
 set testdir [file dirname $argv0]
 source $testdir/tester.tcl
@@ -80,10 +80,10 @@ do_test fuzz2-5.0 {
 } {1 {near ",": syntax error}}
 do_test fuzz2-5.1 {
   catchsql {SELECT 1 WHERE 1 == AAAAAA ( * ) BETWEEN + - ~ + "AAAAAA" . AAAAAA | RAISE ( IGNORE ) COLLATE AAAAAA NOT IN ( SELECT DISTINCT "AAAAAA" . * , * , * WHERE ( SELECT ALL AAAAAA AS "AAAAAA" HAVING CAST ( "AAAAAA" . "AAAAAA" . "AAAAAA" AS AAAAAA ) ORDER BY , , IS NULL ASC , ~ AND DESC LIMIT ( ( "AAAAAA" ) NOT BETWEEN ( ) NOT IN ( ) AND AAAAAA ( ) IS NOT NULL ) OFFSET AAAAAA ( ALL , , ) ) GROUP BY ORDER BY "AAAAAA" . AAAAAA ASC , NULL IN ( SELECT UNION ALL SELECT ALL WHERE HAVING ORDER BY LIMIT UNION SELECT DISTINCT FROM ( ) WHERE + HAVING >> ORDER BY LIMIT . . , "AAAAAA" ) , CAST ( ~ "AAAAAA" . AAAAAA AS "AAAAAA" AAAAAA "AAAAAA" ( + 4294967295 , - 4294967296.0 ) ) ASC LIMIT AAAAAA INTERSECT SELECT ALL * GROUP BY , AAAAAA ( DISTINCT , ) != #241 NOT IN ( , , ) , , CTIME_KW HAVING AAAAAA ORDER BY #103 DESC , #81 ASC LIMIT AAAAAA OFFSET ~ AAAAAA ( ALL AAAAAA . AAAAAA >= AAAAAA . "AAAAAA" . "AAAAAA" ) ) NOTNULL NOT NULL}
-} {1 {near "#81": syntax error}}
+} {1 {near ",": syntax error}}
 do_test fuzz2-5.2 {
   catchsql {SELECT 1 WHERE 1 == AAAAAA ( * ) BETWEEN + - ~ + "AAAAAA" . AAAAAA | RAISE ( IGNORE ) COLLATE AAAAAA NOT IN ( SELECT DISTINCT "AAAAAA" . * , * , * WHERE ( SELECT ALL AAAAAA AS "AAAAAA" HAVING CAST ( "AAAAAA" . "AAAAAA" . "AAAAAA" AS AAAAAA ) ORDER BY , , IS NULL ASC , ~ AND DESC LIMIT ( ( "AAAAAA" ) NOT BETWEEN ( ) NOT IN ( ) AND AAAAAA ( ) IS NOT NULL ) OFFSET AAAAAA ( ALL , , ) ) GROUP BY ORDER BY "AAAAAA" . AAAAAA ASC , NULL IN ( SELECT UNION ALL SELECT ALL WHERE HAVING ORDER BY LIMIT UNION SELECT DISTINCT FROM ( ) WHERE + HAVING >> ORDER BY LIMIT . . , "AAAAAA" ) , CAST ( ~ "AAAAAA" . AAAAAA AS "AAAAAA" AAAAAA "AAAAAA" ( + 4294967295 , - 4294967296.0 ) ) ASC LIMIT AAAAAA INTERSECT SELECT ALL * GROUP BY , AAAAAA ( DISTINCT , ) != #241 NOT IN ( , , ) , , CTIME_KW HAVING AAAAAA ORDER BY #103 DESC , #81 ASC LIMIT AAAAAA OFFSET ~ AAAAAA ( ALL AAAAAA . AAAAAA >= AAAAAA . "AAAAAA" . "AAAAAA" ) ) NOTNULL NOT NULL}
-} {1 {near "#81": syntax error}}
+} {1 {near ",": syntax error}}
 do_test fuzz2-5.3 {
   catchsql {UPDATE "AAAAAA" SET "AAAAAA" = - EXISTS ( SELECT DISTINCT * , * ORDER BY #202 ASC , #147 , ~ AAAAAA . "AAAAAA" ASC LIMIT AAAAAA . "AAAAAA" , RAISE ( ABORT , AAAAAA ) UNION ALL SELECT DISTINCT AAAAAA . * , * FROM ( SELECT DISTINCT}
 } {1 {near "DISTINCT": syntax error}}