Using C libraries in newLISP

The past couple of articles have been tutorials on how to use CFFI to access functions from C libraries in Lisp. Out of completeness, I thought I’d write a short tutorial demonstrating how much easier it is to do the same thing in newLisp. As newLisp is an entirely interpreted language, this built in functionality allows very easy extension of the language using much more low level and efficient libraries.

newLisp uses the ‘import function to define a function from a foreign library. The syntax is (import file-path func-name). For example, if we wished to use libmysqlclient, as in the previous tutorials,

(setq libmysqlclient "/path/to/libmysqlclient.15.dylib")
(import libmysqlclient "mysql_init")
(import libmysqlclient "mysql_close")

Now, both mysql_init and mysql_close have been wrapped for us and can be used as regular newLisp functions. From the MySQL C API docs, we know that mysql_init takes a pointer as a parameter and returns a pointer to a MYSQL type struct. In newLisp, calling the function with a NULL pointer and assigning the new MYSQL pointer is as easy as,

(setq *mysql* (mysql_init 0))

That’s it. The symbols mysql now returns a foreign address. Since we don’t ever need to access it, we can simply pass mysql to our other functions, such as mysql_close, directly:
<

(mysql_close *mysql*)
The MySQL docs describe mysql_real_connect as:
<pre lang="c">MYSQL *mysql_real_connect(MYSQL *mysql, const char *host,
    const char *user, const char *passwd, const char *db, unsigned int port,
    const char *unix_socket, unsigned long client_flag)

That’s a long definition, but it accepts NULL for the last four arguments. So, in newLisp:

(mysql_real_connect *mysql* "someuser" "secret" "mydatabase" 0 0 0)

Easy! This will reassign mysql if successful or return NULL if it fails (it is a destructive function). To test for this, we can define our own simple wrapper for convenience:

(define (connect host user pass (db 0) (port 0) (socket 0))
    (not (zero? (mysql_real_connect *mysql* host user pass db
        port socket 0))))

This accepts our parameters and defaults db, port, and socket to C NULL. It then calls the function and verifies evaluates to true or nil, depending on whether or not the function returned 0, which is the C NULL.

Next, we will discuss how to run a query and access results stored in a struct. Note: I never wrote the second part to this article. Sorry.

Leave a comment | Trackback
Jul 14th, 2007 | Posted in Programming
Tags: ,
No comments yet.