Bring SDBM_File.xs into line with new typemap
[p5sagit/p5-mst-13.2.git] / ext / SDBM_File / SDBM_File.xs
1 #include "EXTERN.h"
2 #include "perl.h"
3 #include "XSUB.h"
4 #include "sdbm/sdbm.h"
5
6 typedef struct {
7         DBM *   dbp ;
8         SV *    filter_fetch_key ;
9         SV *    filter_store_key ;
10         SV *    filter_fetch_value ;
11         SV *    filter_store_value ;
12         int     filtering ;
13         } SDBM_File_type;
14
15 typedef SDBM_File_type * SDBM_File ;
16 typedef datum datum_key ;
17 typedef datum datum_value ;
18
19 #define ckFilter(arg,type,name)                                 \
20         if (db->type) {                                         \
21             SV * save_defsv ;                                   \
22             /* printf("filtering %s\n", name) ;*/               \
23             if (db->filtering)                                  \
24                 croak("recursion detected in %s", name) ;       \
25             db->filtering = TRUE ;                              \
26             /* SAVE_DEFSV ;*/   /* save $_ */                   \
27             save_defsv = newSVsv(DEFSV) ;                       \
28             sv_setsv(DEFSV, arg) ;                              \
29             PUSHMARK(sp) ;                                      \
30             (void) perl_call_sv(db->type, G_DISCARD|G_NOARGS);  \
31             /* SPAGAIN ; */                                             \
32             sv_setsv(arg, DEFSV) ;                              \
33             sv_setsv(DEFSV, save_defsv) ;                               \
34             SvREFCNT_dec(save_defsv) ;                          \
35             /* PUTBACK ; */                                             \
36             db->filtering = FALSE ;                             \
37             /*printf("end of filtering %s\n", name) ;*/         \
38         }
39
40 #define sdbm_TIEHASH(dbtype,filename,flags,mode) sdbm_open(filename,flags,mode)
41 #define sdbm_FETCH(db,key)                      sdbm_fetch(db->dbp,key)
42 #define sdbm_STORE(db,key,value,flags)          sdbm_store(db->dbp,key,value,flags)
43 #define sdbm_DELETE(db,key)                     sdbm_delete(db->dbp,key)
44 #define sdbm_EXISTS(db,key)                     sdbm_exists(db->dbp,key)
45 #define sdbm_FIRSTKEY(db)                       sdbm_firstkey(db->dbp)
46 #define sdbm_NEXTKEY(db,key)                    sdbm_nextkey(db->dbp)
47
48
49 MODULE = SDBM_File      PACKAGE = SDBM_File     PREFIX = sdbm_
50
51 SDBM_File
52 sdbm_TIEHASH(dbtype, filename, flags, mode)
53         char *          dbtype
54         char *          filename
55         int             flags
56         int             mode
57         CODE:
58         {
59             DBM *       dbp ;
60
61             RETVAL = NULL ;
62             if (dbp = sdbm_open(filename,flags,mode) ) {
63                 RETVAL = (SDBM_File)safemalloc(sizeof(SDBM_File_type)) ;
64                 Zero(RETVAL, 1, SDBM_File_type) ;
65                 RETVAL->dbp = dbp ;
66             }
67             
68         }
69         OUTPUT:
70           RETVAL
71
72 void
73 sdbm_DESTROY(db)
74         SDBM_File       db
75         CODE:
76           sdbm_close(db->dbp);
77           if (db->filter_fetch_key)
78             SvREFCNT_dec(db->filter_fetch_key) ;
79           if (db->filter_store_key)
80             SvREFCNT_dec(db->filter_store_key) ;
81           if (db->filter_fetch_value)
82             SvREFCNT_dec(db->filter_fetch_value) ;
83           if (db->filter_store_value)
84             SvREFCNT_dec(db->filter_store_value) ;
85           Safefree(db) ;        
86
87 datum_value
88 sdbm_FETCH(db, key)
89         SDBM_File       db
90         datum_key       key
91
92 int
93 sdbm_STORE(db, key, value, flags = DBM_REPLACE)
94         SDBM_File       db
95         datum_key       key
96         datum_value     value
97         int             flags
98     CLEANUP:
99         if (RETVAL) {
100             if (RETVAL < 0 && errno == EPERM)
101                 croak("No write permission to sdbm file");
102             croak("sdbm store returned %d, errno %d, key \"%s\"",
103                         RETVAL,errno,key.dptr);
104             sdbm_clearerr(db->dbp);
105         }
106
107 int
108 sdbm_DELETE(db, key)
109         SDBM_File       db
110         datum_key       key
111
112 int
113 sdbm_EXISTS(db,key)
114         SDBM_File       db
115         datum_key       key
116
117 datum_key
118 sdbm_FIRSTKEY(db)
119         SDBM_File       db
120
121 datum_key
122 sdbm_NEXTKEY(db, key)
123         SDBM_File       db
124         datum_key       key
125
126 int
127 sdbm_error(db)
128         SDBM_File       db
129         CODE:
130         RETVAL = sdbm_error(db->dbp) ;
131         OUTPUT:
132           RETVAL
133
134 int
135 sdbm_clearerr(db)
136         SDBM_File       db
137         CODE:
138         RETVAL = sdbm_clearerr(db->dbp) ;
139         OUTPUT:
140           RETVAL
141
142
143 #define setFilter(type)                                 \
144         {                                               \
145             if (db->type)                               \
146                 RETVAL = newSVsv(db->type) ;            \
147             if (db->type && (code == &PL_sv_undef)) {   \
148                 SvREFCNT_dec(db->type) ;                \
149                 db->type = NULL ;                       \
150             }                                           \
151             else if (code) {                            \
152                 if (db->type)                           \
153                     sv_setsv(db->type, code) ;          \
154                 else                                    \
155                     db->type = newSVsv(code) ;          \
156             }                                           \
157         }
158
159
160
161 SV *
162 filter_fetch_key(db, code)
163         SDBM_File       db
164         SV *            code
165         SV *            RETVAL = &PL_sv_undef ;
166         CODE:
167             setFilter(filter_fetch_key) ;
168         OUTPUT:
169             RETVAL
170
171 SV *
172 filter_store_key(db, code)
173         SDBM_File       db
174         SV *            code
175         SV *            RETVAL =  &PL_sv_undef ;
176         CODE:
177             setFilter(filter_store_key) ;
178         OUTPUT:
179             RETVAL
180
181 SV *
182 filter_fetch_value(db, code)
183         SDBM_File       db
184         SV *            code
185         SV *            RETVAL =  &PL_sv_undef ;
186         CODE:
187             setFilter(filter_fetch_value) ;
188         OUTPUT:
189             RETVAL
190
191 SV *
192 filter_store_value(db, code)
193         SDBM_File       db
194         SV *            code
195         SV *            RETVAL =  &PL_sv_undef ;
196         CODE:
197             setFilter(filter_store_value) ;
198         OUTPUT:
199             RETVAL
200