xref: /PHP-8.1/ext/dba/dba_db1.c (revision 01b3fc03)
1 /*
2    +----------------------------------------------------------------------+
3    | Copyright (c) The PHP Group                                          |
4    +----------------------------------------------------------------------+
5    | This source file is subject to version 3.01 of the PHP license,      |
6    | that is bundled with this package in the file LICENSE, and is        |
7    | available through the world-wide-web at the following url:           |
8    | https://www.php.net/license/3_01.txt                                 |
9    | If you did not receive a copy of the PHP license and are unable to   |
10    | obtain it through the world-wide-web, please send a note to          |
11    | license@php.net so we can mail you a copy immediately.               |
12    +----------------------------------------------------------------------+
13    | Author: Shen Cheng-Da <cdsheen@gmail.com>                            |
14    +----------------------------------------------------------------------+
15  */
16 
17 #ifdef HAVE_CONFIG_H
18 #include "config.h"
19 #endif
20 
21 #include "php.h"
22 
23 #if DBA_DB1
24 #include "php_db1.h"
25 
26 #ifdef DB1_INCLUDE_FILE
27 #include DB1_INCLUDE_FILE
28 #endif
29 
30 #include <sys/types.h>
31 #include <sys/stat.h>
32 #include <fcntl.h>
33 
34 #define DB1_DATA dba_db1_data *dba = info->dbf
35 #define DB1_GKEY DBT gkey; gkey.data = (char *) key; gkey.size = keylen
36 
37 typedef struct {
38 	DB  *dbp;
39 } dba_db1_data;
40 
DBA_OPEN_FUNC(db1)41 DBA_OPEN_FUNC(db1)
42 {
43 	dba_db1_data	*dba;
44 	DB		*db;
45 
46 	int gmode;
47 	int filemode = 0644;
48 
49 	if (info->argc > 0) {
50 		filemode = zval_get_long(&info->argv[0]);
51 	}
52 
53 	gmode = 0;
54 	switch (info->mode) {
55 		case DBA_READER:
56 			gmode = O_RDONLY;
57 			break;
58 		case DBA_WRITER:
59 			gmode = O_RDWR;
60 			break;
61 		case DBA_CREAT:
62 			gmode = O_RDWR | O_CREAT;
63 			break;
64 		case DBA_TRUNC:
65 			gmode = O_RDWR | O_CREAT | O_TRUNC;
66 			break;
67 		default:
68 			return FAILURE; /* not possible */
69 	}
70 
71 	db = dbopen((char *)info->path, gmode, filemode, DB_HASH, NULL);
72 
73 	if (db == NULL) {
74 		return FAILURE;
75 	}
76 
77 	dba = pemalloc(sizeof(*dba), info->flags&DBA_PERSISTENT);
78 	dba->dbp = db;
79 
80 	info->dbf = dba;
81 
82 	return SUCCESS;
83 }
84 
DBA_CLOSE_FUNC(db1)85 DBA_CLOSE_FUNC(db1)
86 {
87 	DB1_DATA;
88 	dba->dbp->close(dba->dbp);
89 	pefree(info->dbf, info->flags&DBA_PERSISTENT);
90 }
91 
DBA_FETCH_FUNC(db1)92 DBA_FETCH_FUNC(db1)
93 {
94 	DBT gval;
95 	DB1_DATA;
96 	DB1_GKEY;
97 
98 	memset(&gval, 0, sizeof(gval));
99 	if (dba->dbp->get(dba->dbp, &gkey, &gval, 0) == RET_SUCCESS) {
100 		if (newlen) *newlen = gval.size;
101 		return estrndup(gval.data, gval.size);
102 	}
103 	return NULL;
104 }
105 
DBA_UPDATE_FUNC(db1)106 DBA_UPDATE_FUNC(db1)
107 {
108 	DBT gval;
109 	DB1_DATA;
110 	DB1_GKEY;
111 
112 	gval.data = (char *) val;
113 	gval.size = vallen;
114 
115 	return dba->dbp->put(dba->dbp, &gkey, &gval, mode == 1 ? R_NOOVERWRITE : 0) != RET_SUCCESS ? FAILURE : SUCCESS;
116 }
117 
DBA_EXISTS_FUNC(db1)118 DBA_EXISTS_FUNC(db1)
119 {
120 	DBT gval;
121 	DB1_DATA;
122 	DB1_GKEY;
123 
124 	return dba->dbp->get(dba->dbp, &gkey, &gval, 0) != RET_SUCCESS ? FAILURE : SUCCESS;
125 }
126 
DBA_DELETE_FUNC(db1)127 DBA_DELETE_FUNC(db1)
128 {
129 	DB1_DATA;
130 	DB1_GKEY;
131 
132 	return dba->dbp->del(dba->dbp, &gkey, 0) != RET_SUCCESS ? FAILURE : SUCCESS;
133 }
134 
DBA_FIRSTKEY_FUNC(db1)135 DBA_FIRSTKEY_FUNC(db1)
136 {
137 	DBT gkey;
138 	DBT gval;
139 	DB1_DATA;
140 
141 	memset(&gkey, 0, sizeof(gkey));
142 	memset(&gval, 0, sizeof(gval));
143 
144 	if (dba->dbp->seq(dba->dbp, &gkey, &gval, R_FIRST) == RET_SUCCESS) {
145 		if (newlen) *newlen = gkey.size;
146 		return estrndup(gkey.data, gkey.size);
147 	}
148 	return NULL;
149 }
150 
DBA_NEXTKEY_FUNC(db1)151 DBA_NEXTKEY_FUNC(db1)
152 {
153 	DBT gkey;
154 	DBT gval;
155 	DB1_DATA;
156 
157 	memset(&gkey, 0, sizeof(gkey));
158 	memset(&gval, 0, sizeof(gval));
159 
160 	if (dba->dbp->seq(dba->dbp, &gkey, &gval, R_NEXT) == RET_SUCCESS) {
161 		if (newlen) *newlen = gkey.size;
162 		return estrndup(gkey.data, gkey.size);
163 	}
164 	return NULL;
165 }
166 
DBA_OPTIMIZE_FUNC(db1)167 DBA_OPTIMIZE_FUNC(db1)
168 {
169 	/* dummy */
170 	return SUCCESS;
171 }
172 
DBA_SYNC_FUNC(db1)173 DBA_SYNC_FUNC(db1)
174 {
175 	return SUCCESS;
176 }
177 
DBA_INFO_FUNC(db1)178 DBA_INFO_FUNC(db1)
179 {
180 	return estrdup(DB1_VERSION);
181 }
182 
183 #endif
184