Skip to content

Commit 8f3e1ce

Browse files
committed
package: add ABI version checking
jim.h now includes JIM_ABI_VERSION that should be incremented whenever the ABI changes. Then all loadable modules should call Jim_CheckAbiVersion() to make sure they are loaded against the correct version. Add Jim_PackageProvideCheck() that does both Jim_CheckAbiVersion() and Jim_PackageProvide() to simplify the implementation of loadable extensions. Also rename the "big" sqlite3 extension to just sqlite to avoid a naming conflict with the smaller jim-sqlite3 extension. Signed-off-by: Steve Bennett <[email protected]>
1 parent a956477 commit 8f3e1ce

28 files changed

+62
-88
lines changed

jim-array.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -259,9 +259,7 @@ static const jim_subcmd_type array_command_table[] = {
259259

260260
int Jim_arrayInit(Jim_Interp *interp)
261261
{
262-
if (Jim_PackageProvide(interp, "array", "1.0", JIM_ERRMSG))
263-
return JIM_ERR;
264-
262+
Jim_PackageProvideCheck(interp, "array");
265263
Jim_CreateCommand(interp, "array", Jim_SubCmdProc, (void *)array_command_table, NULL);
266264
return JIM_OK;
267265
}

jim-clock.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -228,9 +228,7 @@ static const jim_subcmd_type clock_command_table[] = {
228228

229229
int Jim_clockInit(Jim_Interp *interp)
230230
{
231-
if (Jim_PackageProvide(interp, "clock", "1.0", JIM_ERRMSG))
232-
return JIM_ERR;
233-
231+
Jim_PackageProvideCheck(interp, "clock");
234232
Jim_CreateCommand(interp, "clock", Jim_SubCmdProc, (void *)clock_command_table, NULL);
235233
return JIM_OK;
236234
}

jim-eventloop.c

+1-2
Original file line numberDiff line numberDiff line change
@@ -794,8 +794,7 @@ int Jim_eventloopInit(Jim_Interp *interp)
794794
{
795795
Jim_EventLoop *eventLoop;
796796

797-
if (Jim_PackageProvide(interp, "eventloop", "1.0", JIM_ERRMSG))
798-
return JIM_ERR;
797+
Jim_PackageProvideCheck(interp, "eventloop");
799798

800799
eventLoop = Jim_Alloc(sizeof(*eventLoop));
801800
memset(eventLoop, 0, sizeof(*eventLoop));

jim-exec.c

+3-5
Original file line numberDiff line numberDiff line change
@@ -82,9 +82,7 @@ static int Jim_ExecCmd(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
8282

8383
int Jim_execInit(Jim_Interp *interp)
8484
{
85-
if (Jim_PackageProvide(interp, "exec", "1.0", JIM_ERRMSG))
86-
return JIM_ERR;
87-
85+
Jim_PackageProvideCheck(interp, "exec");
8886
Jim_CreateCommand(interp, "exec", Jim_ExecCmd, NULL, NULL);
8987
return JIM_OK;
9088
}
@@ -1230,8 +1228,8 @@ static int JimCleanupChildren(Jim_Interp *interp, int numPids, pidtype *pidPtr,
12301228
int Jim_execInit(Jim_Interp *interp)
12311229
{
12321230
struct WaitInfoTable *waitinfo;
1233-
if (Jim_PackageProvide(interp, "exec", "1.0", JIM_ERRMSG))
1234-
return JIM_ERR;
1231+
1232+
Jim_PackageProvideCheck(interp, "exec");
12351233

12361234
waitinfo = JimAllocWaitInfoTable();
12371235
Jim_CreateCommand(interp, "exec", Jim_ExecCmd, waitinfo, JimFreeWaitInfoTable);

jim-file.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -1119,9 +1119,7 @@ static int Jim_PwdCmd(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
11191119

11201120
int Jim_fileInit(Jim_Interp *interp)
11211121
{
1122-
if (Jim_PackageProvide(interp, "file", "1.0", JIM_ERRMSG))
1123-
return JIM_ERR;
1124-
1122+
Jim_PackageProvideCheck(interp, "file");
11251123
Jim_CreateCommand(interp, "file", Jim_SubCmdProc, (void *)file_command_table, NULL);
11261124
Jim_CreateCommand(interp, "pwd", Jim_PwdCmd, NULL, NULL);
11271125
Jim_CreateCommand(interp, "cd", Jim_CdCmd, NULL, NULL);

jim-history.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -113,9 +113,7 @@ static const jim_subcmd_type history_command_table[] = {
113113

114114
int Jim_historyInit(Jim_Interp *interp)
115115
{
116-
if (Jim_PackageProvide(interp, "history", "1.0", JIM_ERRMSG))
117-
return JIM_ERR;
118-
116+
Jim_PackageProvideCheck(interp, "history");
119117
Jim_CreateCommand(interp, "history", Jim_SubCmdProc, (void *)history_command_table, NULL);
120118
return JIM_OK;
121119
}

jim-interp.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -169,9 +169,7 @@ static int JimInterpCommand(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
169169

170170
int Jim_interpInit(Jim_Interp *interp)
171171
{
172-
if (Jim_PackageProvide(interp, "interp", "1.0", JIM_ERRMSG))
173-
return JIM_ERR;
174-
172+
Jim_PackageProvideCheck(interp, "interp");
175173
Jim_CreateCommand(interp, "interp", JimInterpCommand, NULL, NULL);
176174

177175
return JIM_OK;

jim-json.c

+1-4
Original file line numberDiff line numberDiff line change
@@ -418,10 +418,7 @@ json_decode(Jim_Interp *interp, int argc, Jim_Obj *const argv[])
418418
int
419419
Jim_jsonInit(Jim_Interp *interp)
420420
{
421-
if (Jim_PackageProvide(interp, "json", "1.0", JIM_ERRMSG) != JIM_OK) {
422-
return JIM_ERR;
423-
}
424-
421+
Jim_PackageProvideCheck(interp, "json");
425422
Jim_CreateCommand(interp, "json::decode", json_decode, NULL, NULL);
426423
/* Load the Tcl implementation of the json encoder if possible */
427424
Jim_PackageRequire(interp, "jsonencode", 0);

jim-namespace.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -324,9 +324,7 @@ static int JimNamespaceCmd(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
324324

325325
int Jim_namespaceInit(Jim_Interp *interp)
326326
{
327-
if (Jim_PackageProvide(interp, "namespace", "1.0", JIM_ERRMSG))
328-
return JIM_ERR;
329-
327+
Jim_PackageProvideCheck(interp, "namespace");
330328
Jim_CreateCommand(interp, "namespace", JimNamespaceCmd, NULL, NULL);
331329
Jim_CreateCommand(interp, "variable", JimVariableCmd, NULL, NULL);
332330
return JIM_OK;

jim-pack.c

+1-4
Original file line numberDiff line numberDiff line change
@@ -475,10 +475,7 @@ static int Jim_PackCmd(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
475475

476476
int Jim_packInit(Jim_Interp *interp)
477477
{
478-
if (Jim_PackageProvide(interp, "pack", "1.0", JIM_ERRMSG)) {
479-
return JIM_ERR;
480-
}
481-
478+
Jim_PackageProvideCheck(interp, "pack");
482479
Jim_CreateCommand(interp, "unpack", Jim_UnpackCmd, NULL, NULL);
483480
Jim_CreateCommand(interp, "pack", Jim_PackCmd, NULL, NULL);
484481
return JIM_OK;

jim-posix.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -137,9 +137,7 @@ static int Jim_PosixUptimeCommand(Jim_Interp *interp, int argc, Jim_Obj *const *
137137

138138
int Jim_posixInit(Jim_Interp *interp)
139139
{
140-
if (Jim_PackageProvide(interp, "posix", "1.0", JIM_ERRMSG))
141-
return JIM_ERR;
142-
140+
Jim_PackageProvideCheck(interp, "posix");
143141
#ifdef HAVE_FORK
144142
Jim_CreateCommand(interp, "os.fork", Jim_PosixForkCommand, NULL, NULL);
145143
#endif

jim-readdir.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -114,9 +114,7 @@ int Jim_ReaddirCmd(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
114114

115115
int Jim_readdirInit(Jim_Interp *interp)
116116
{
117-
if (Jim_PackageProvide(interp, "readdir", "1.0", JIM_ERRMSG))
118-
return JIM_ERR;
119-
117+
Jim_PackageProvideCheck(interp, "readdir");
120118
Jim_CreateCommand(interp, "readdir", Jim_ReaddirCmd, NULL, NULL);
121119
return JIM_OK;
122120
}

jim-readline.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -65,9 +65,7 @@ static int JimRlAddHistoryCommand(Jim_Interp *interp, int argc, Jim_Obj *const *
6565

6666
int Jim_readlineInit(Jim_Interp *interp)
6767
{
68-
if (Jim_PackageProvide(interp, "readline", "1.0", JIM_ERRMSG))
69-
return JIM_ERR;
70-
68+
Jim_PackageProvideCheck(interp, "readline");
7169
Jim_CreateCommand(interp, "readline.readline", JimRlReadlineCommand, NULL, NULL);
7270
Jim_CreateCommand(interp, "readline.addhistory", JimRlAddHistoryCommand, NULL, NULL);
7371
return JIM_OK;

jim-redis.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -163,9 +163,7 @@ static int jim_redis_cmd(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
163163
int
164164
Jim_redisInit(Jim_Interp *interp)
165165
{
166-
if (Jim_PackageProvide(interp, "redis", "1.0", JIM_ERRMSG))
167-
return JIM_ERR;
168-
166+
Jim_PackageProvideCheck(interp, "redis");
169167
Jim_CreateCommand(interp, "redis", jim_redis_cmd, NULL, NULL);
170168
return JIM_OK;
171169
}

jim-regexp.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -581,9 +581,7 @@ int Jim_RegsubCmd(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
581581

582582
int Jim_regexpInit(Jim_Interp *interp)
583583
{
584-
if (Jim_PackageProvide(interp, "regexp", "1.0", JIM_ERRMSG))
585-
return JIM_ERR;
586-
584+
Jim_PackageProvideCheck(interp, "regexp");
587585
Jim_CreateCommand(interp, "regexp", Jim_RegexpCmd, NULL, NULL);
588586
Jim_CreateCommand(interp, "regsub", Jim_RegsubCmd, NULL, NULL);
589587
return JIM_OK;

jim-sdl.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -535,9 +535,7 @@ static int JimSdlSurfaceCommand(Jim_Interp *interp, int argc, Jim_Obj *const *ar
535535

536536
int Jim_sdlInit(Jim_Interp *interp)
537537
{
538-
if (Jim_PackageProvide(interp, "sdl", "1.0", JIM_ERRMSG))
539-
return JIM_ERR;
540-
538+
Jim_PackageProvideCheck(interp, "sdl");
541539
Jim_CreateCommand(interp, "sdl.screen", JimSdlSurfaceCommand, NULL, NULL);
542540
return JIM_OK;
543541
}

jim-signal.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -530,9 +530,7 @@ static int Jim_KillCmd(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
530530

531531
int Jim_signalInit(Jim_Interp *interp)
532532
{
533-
if (Jim_PackageProvide(interp, "signal", "1.0", JIM_ERRMSG))
534-
return JIM_ERR;
535-
533+
Jim_PackageProvideCheck(interp, "signal");
536534
Jim_CreateCommand(interp, "alarm", Jim_AlarmCmd, 0, 0);
537535
Jim_CreateCommand(interp, "kill", Jim_KillCmd, 0, 0);
538536
/* Sleep is slightly dubious here */

jim-sqlite3.c

+1-3
Original file line numberDiff line numberDiff line change
@@ -288,9 +288,7 @@ static int JimSqliteOpenCommand(Jim_Interp *interp, int argc, Jim_Obj *const *ar
288288

289289
int Jim_sqlite3Init(Jim_Interp *interp)
290290
{
291-
if (Jim_PackageProvide(interp, "sqlite3", "1.0", JIM_ERRMSG))
292-
return JIM_ERR;
293-
291+
Jim_PackageProvideCheck(interp, "sqlite3");
294292
Jim_CreateCommand(interp, "sqlite3.open", JimSqliteOpenCommand, NULL, NULL);
295293
return JIM_OK;
296294
}

jim-syslog.c

+1-2
Original file line numberDiff line numberDiff line change
@@ -172,8 +172,7 @@ int Jim_syslogInit(Jim_Interp *interp)
172172
{
173173
SyslogInfo *info;
174174

175-
if (Jim_PackageProvide(interp, "syslog", "1.0", JIM_ERRMSG))
176-
return JIM_ERR;
175+
Jim_PackageProvideCheck(interp, "syslog");
177176

178177
info = Jim_Alloc(sizeof(*info));
179178

jim-tclprefix.c

+1-4
Original file line numberDiff line numberDiff line change
@@ -214,10 +214,7 @@ static int Jim_TclPrefixCoreCommand(Jim_Interp *interp, int argc, Jim_Obj *const
214214

215215
int Jim_tclprefixInit(Jim_Interp *interp)
216216
{
217-
if (Jim_PackageProvide(interp, "tclprefix", "1.0", JIM_ERRMSG)) {
218-
return JIM_ERR;
219-
}
220-
217+
Jim_PackageProvideCheck(interp, "tclprefix");
221218
Jim_CreateCommand(interp, "tcl::prefix", Jim_TclPrefixCoreCommand, NULL, NULL);
222219
return JIM_OK;
223220
}

jim-win32.c

+1-2
Original file line numberDiff line numberDiff line change
@@ -506,8 +506,7 @@ Win32_MessageBox(Jim_Interp *interp, int objc, Jim_Obj * const *objv)
506506
int
507507
Jim_win32Init(Jim_Interp *interp)
508508
{
509-
if (Jim_PackageProvide(interp, "win32", "1.0", JIM_ERRMSG))
510-
return JIM_ERR;
509+
Jim_PackageProvideCheck(interp, "win32");
511510

512511
#define CMD(name) \
513512
Jim_CreateCommand(interp, "win32." #name , Win32_ ## name , NULL, NULL)

jim-zlib.c

+1-4
Original file line numberDiff line numberDiff line change
@@ -309,10 +309,7 @@ static int JimZlibCmd(Jim_Interp *interp, int argc, Jim_Obj *const *argv)
309309

310310
int Jim_zlibInit(Jim_Interp *interp)
311311
{
312-
if (Jim_PackageProvide(interp, "zlib", "1.0", JIM_ERRMSG)) {
313-
return JIM_ERR;
314-
}
315-
312+
Jim_PackageProvideCheck(interp, "zlib");
316313
Jim_CreateCommand(interp, "zlib", JimZlibCmd, 0, 0);
317314

318315
return JIM_OK;

jim.c

+13
Original file line numberDiff line numberDiff line change
@@ -16206,6 +16206,19 @@ void Jim_SetResultFormatted(Jim_Interp *interp, const char *format, ...)
1620616206
}
1620716207
}
1620816208

16209+
/* Should be called as the first thing in a loadable module to verify
16210+
* that the interpeter ABI is compatible with the ABI that the module was compiled against.
16211+
* Returns JIM_ERR and sets an error if mismatch.
16212+
*/
16213+
int Jim_CheckAbiVersion(Jim_Interp *interp, int abi_version)
16214+
{
16215+
if (abi_version != JIM_ABI_VERSION) {
16216+
Jim_SetResultString(interp, "ABI version mismatch", -1);
16217+
return JIM_ERR;
16218+
}
16219+
return JIM_OK;
16220+
}
16221+
1620916222
/* stubs */
1621016223
#ifndef jim_ext_package
1621116224
int Jim_PackageProvide(Jim_Interp *interp, const char *name, const char *ver, int flags)

jim.h

+8
Original file line numberDiff line numberDiff line change
@@ -125,6 +125,9 @@ extern "C" {
125125
* Exported defines
126126
* ---------------------------------------------------------------------------*/
127127

128+
/* Increment this every time the public ABI changes */
129+
#define JIM_ABI_VERSION 100
130+
128131
#define JIM_OK 0
129132
#define JIM_ERR 1
130133
#define JIM_RETURN 2
@@ -891,13 +894,18 @@ JIM_EXPORT void * Jim_GetAssocData(Jim_Interp *interp, const char *key);
891894
JIM_EXPORT int Jim_SetAssocData(Jim_Interp *interp, const char *key,
892895
Jim_InterpDeleteProc *delProc, void *data);
893896
JIM_EXPORT int Jim_DeleteAssocData(Jim_Interp *interp, const char *key);
897+
JIM_EXPORT int Jim_CheckAbiVersion(Jim_Interp *interp, int abi_version);
894898

895899
/* Packages C API */
900+
896901
/* jim-package.c */
897902
JIM_EXPORT int Jim_PackageProvide (Jim_Interp *interp,
898903
const char *name, const char *ver, int flags);
899904
JIM_EXPORT int Jim_PackageRequire (Jim_Interp *interp,
900905
const char *name, int flags);
906+
#define Jim_PackageProvideCheck(INTERP, NAME) \
907+
if (Jim_CheckAbiVersion(INTERP, JIM_ABI_VERSION) == JIM_ERR || Jim_PackageProvide(INTERP, NAME, "1.0", JIM_ERRMSG)) \
908+
return JIM_ERR
901909

902910
/* error messages */
903911
JIM_EXPORT void Jim_MakeErrorMessage (Jim_Interp *interp);

sqlite3/Makefile

+4-4
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,16 @@
11
# Builds the full sqlite3 extension for Jim Tcl with the sqlite3 amalgamation
22

3-
all: sqlite3.so
3+
all: sqlite.so
44

55
SQLITE3_OPTS := -DSQLITE_OMIT_LOAD_EXTENSION=1 -DSQLITE_THREADSAFE=0 -DSQLITE_DEFAULT_FILE_FORMAT=4 \
66
-DSQLITE_ENABLE_STAT3 -DSQLITE_ENABLE_LOCKING_STYLE=0 -DSQLITE_OMIT_INCRBLOB
77

8-
sqlite3.so: jim-sqlite3.c sqlite3.c
8+
sqlite.so: jim-sqlite.c sqlite3.c
99
./build-ext -Wall -o $@ -I.. -L.. $(SQLITE3_OPTS) $(BUILDOPTS) $^
1010

1111
clean:
1212
rm -f *.o *.so
1313

1414
# Note that this will only work when not cross compiling
15-
test: sqlite3.so
16-
../jimsh test-sqlite3.tcl
15+
test: sqlite.so
16+
../jimsh test-sqlite.tcl

sqlite3/README

+8-8
Original file line numberDiff line numberDiff line change
@@ -13,14 +13,14 @@ Ensure that you have configured and built jim in the source directory, then:
1313

1414
$ make
1515

16-
./build-ext -o sqlite3.so -I.. -L.. -DSQLITE_OMIT_LOAD_EXTENSION=1 ... jim-sqlite3.c sqlite3.c
17-
Building sqlite3.so from jim-sqlite3.c sqlite3.c
16+
./build-ext -o sqlite.so -I.. -L.. -DSQLITE_OMIT_LOAD_EXTENSION=1 ... jim-sqlite.c sqlite3.c
17+
Building sqlite.so from jim-sqlite.c sqlite3.c
1818

1919
Warning: libjim is static. Dynamic module may not work on some platforms.
2020

21-
Compile: jim-sqlite3.o
21+
Compile: jim-sqlite.o
2222
Compile: sqlite3.o
23-
Link: sqlite3.so
23+
Link: sqlite.so
2424

2525
Success!
2626

@@ -32,17 +32,17 @@ $ make test
3232
Installing
3333
----------
3434

35-
Copy sqlite3.so to your jim library directory, typically /usr/local/lib/jim or
35+
Copy sqlite.so to your jim library directory, typically /usr/local/lib/jim or
3636
where $JIMLIB points to.
3737

3838
Using
3939
-----
40-
In your Jim Tcl code, ensure that sqlite3.so is in a directory on $auto_path.
40+
In your Jim Tcl code, ensure that sqlite.so is in a directory on $auto_path.
4141
Then:
4242

43-
package require sqlite3
43+
package require sqlite
4444

45-
sqlite3 db test.db
45+
sqlite db test.db
4646
...etc..
4747

4848
Documentation

sqlite3/jim-sqlite3.c sqlite3/jim-sqlite.c

+2-4
Original file line numberDiff line numberDiff line change
@@ -2821,10 +2821,8 @@ static int DbMain(Jim_Interp *interp, int objc, Jim_Obj *const*objv){
28212821
** used to open a new SQLite database. See the DbMain() routine above
28222822
** for additional information.
28232823
*/
2824-
EXTERN int Jim_sqlite3Init(Jim_Interp *interp){
2825-
Jim_CreateCommand(interp, "sqlite3", DbMain, 0, 0);
2826-
Jim_PackageProvide(interp, "sqlite3", PACKAGE_VERSION, 0);
2824+
EXTERN int Jim_sqliteInit(Jim_Interp *interp){
2825+
Jim_PackageProvideCheck(interp, "sqlite");
28272826
Jim_CreateCommand(interp, "sqlite", DbMain, 0, 0);
2828-
Jim_PackageProvide(interp, "sqlite", PACKAGE_VERSION, 0);
28292827
return JIM_OK;
28302828
}

sqlite3/test-sqlite3.tcl sqlite3/test-sqlite.tcl

+3-3
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,11 @@
1-
# A simple test of the "big" sqlite3 extension
1+
# A simple test of the "big" sqlite extension
22

33
set auto_path [list . {*}$auto_path]
44

5-
package require sqlite3
5+
package require sqlite
66

77
# Create an in-memory database and add some data
8-
sqlite3 db :memory:
8+
sqlite db :memory:
99
db eval {CREATE TABLE history (type, time, value)}
1010
foreach t [range 1 50] {
1111
set temp [rand 100]

0 commit comments

Comments
 (0)