smdb.c
上传用户:xu_441
上传日期:2007-01-04
资源大小:1640k
文件大小:9k
源码类别:

Email客户端

开发平台:

Unix_Linux

  1. /*
  2. ** Copyright (c) 1999 Sendmail, Inc. and its suppliers.
  3. ** All rights reserved.
  4. **
  5. ** By using this file, you agree to the terms and conditions set
  6. ** forth in the LICENSE file which can be found at the top level of
  7. ** the sendmail distribution.
  8. */
  9. #ifndef lint
  10. static char copyright[] =
  11. "@(#) Copyright (c) 1998, 1999 Sendmail, Inc. and its suppliers.n
  12. All rights reserved.n
  13.      Copyright (c) 1983, 1987, 1993n
  14. The Regents of the University of California.  All rights reserved.n
  15.      Copyright (c) 1983 Eric P. Allman.  All rights reserved.n";
  16. #endif /* ! lint */
  17. #ifndef lint
  18. static char id[] = "@(#)$Id: smdb.c,v 8.33 1999/10/13 06:17:07 gshapiro Exp $";
  19. #endif /* ! lint */
  20. #include <fcntl.h>
  21. #include <stdlib.h>
  22. #include <unistd.h>
  23. #include <sendmail/sendmail.h>
  24. #include <libsmdb/smdb.h>
  25. /*
  26. ** SMDB_MALLOC_DATABASE -- Allocates a database structure.
  27. **
  28. ** Parameters:
  29. ** None
  30. **
  31. ** Returns:
  32. ** An pointer to an allocated SMDB_DATABASE structure or
  33. ** NULL if it couldn't allocate the memory.
  34. */
  35. SMDB_DATABASE *
  36. smdb_malloc_database()
  37. {
  38. SMDB_DATABASE *db;
  39. db = (SMDB_DATABASE *) malloc(sizeof(SMDB_DATABASE));
  40. if (db != NULL)
  41. memset(db, '', sizeof(SMDB_DATABASE));
  42. return db;
  43. }
  44. /*
  45. ** SMDB_FREE_DATABASE -- Unallocates a database structure.
  46. **
  47. ** Parameters:
  48. ** database -- a SMDB_DATABASE pointer to deallocate.
  49. **
  50. ** Returns:
  51. ** None
  52. */
  53. void
  54. smdb_free_database(database)
  55. SMDB_DATABASE *database;
  56. {
  57. if (database != NULL)
  58. free(database);
  59. }
  60. /*
  61. ** SMDB_OPEN_DATABASE -- Opens a database.
  62. **
  63. ** This opens a database. If type is SMDB_DEFAULT it tries to
  64. ** use a DB1 or DB2 hash. If that isn't available, it will try
  65. ** to use NDBM. If a specific type is given it will try to open
  66. ** a database of that type.
  67. **
  68. ** Parameters:
  69. ** database -- An pointer to a SMDB_DATABASE pointer where the
  70. **    opened database will be stored. This should
  71. **    be unallocated.
  72. ** db_name -- The name of the database to open. Do not include
  73. **   the file name extension.
  74. ** mode -- The mode to set on the database file or files.
  75. ** mode_mask -- Mode bits that must match on an opened database.
  76. ** sff -- Flags to safefile.
  77. ** type -- The type of database to open. Supported types
  78. **        vary depending on what was compiled in.
  79. ** user_info -- Information on the user to use for file
  80. **     permissions.
  81. ** params -- Params specific to the database being opened.
  82. **  Only supports some DB hash options right now
  83. **  (see smdb_db_open() for details).
  84. **
  85. ** Returns:
  86. ** SMDBE_OK -- Success.
  87. ** Anything else is an error. Look up more info about the
  88. ** error in the comments for the specific open() used.
  89. */
  90. int
  91. smdb_open_database(database, db_name, mode, mode_mask, sff, type, user_info,
  92.    params)
  93. SMDB_DATABASE **database;
  94. char *db_name;
  95. int mode;
  96. int mode_mask;
  97. int sff;
  98. SMDB_DBTYPE type;
  99. SMDB_USER_INFO *user_info;
  100. SMDB_DBPARAMS *params;
  101. {
  102. int result;
  103. #ifdef NEWDB
  104. if (type == SMDB_TYPE_DEFAULT)
  105. type = SMDB_TYPE_HASH;
  106. #endif /* NEWDB */
  107. #ifdef NDBM
  108. if (type == SMDB_TYPE_DEFAULT)
  109. type = SMDB_TYPE_NDBM;
  110. #endif /* NDBM */
  111. if (type == SMDB_TYPE_DEFAULT)
  112. return SMDBE_UNKNOWN_DB_TYPE;
  113. if (strncmp(type, SMDB_TYPE_NDBM, SMDB_TYPE_NDBM_LEN) == 0)
  114. {
  115. #ifdef NDBM
  116. result = smdb_ndbm_open(database, db_name, mode, mode_mask,
  117. sff, type, user_info, params);
  118. return result;
  119. #else /* NDBM */
  120. return SMDBE_UNSUPPORTED_DB_TYPE;
  121. #endif /* NDBM */
  122. }
  123. if ((strncmp(type, SMDB_TYPE_HASH, SMDB_TYPE_HASH_LEN) == 0) ||
  124.     (strncmp(type, SMDB_TYPE_BTREE, SMDB_TYPE_BTREE_LEN) == 0))
  125. {
  126. #ifdef NEWDB
  127. result = smdb_db_open(database, db_name, mode, mode_mask, sff,
  128.       type, user_info, params);
  129. return result;
  130. #else /* NEWDB */
  131. return SMDBE_UNSUPPORTED_DB_TYPE;
  132. #endif /* NEWDB */
  133. }
  134. return SMDBE_UNKNOWN_DB_TYPE;
  135. }
  136. /*
  137. ** SMDB_ADD_EXTENSION -- Adds an extension to a file name.
  138. **
  139. ** Just adds a . followed by a string to a db_name if there
  140. ** is room and the db_name does not already have that extension.
  141. **
  142. ** Parameters:
  143. ** full_name -- The final file name.
  144. ** max_full_name_len -- The max length for full_name.
  145. ** db_name -- The name of the db.
  146. ** extension -- The extension to add.
  147. **
  148. ** Returns:
  149. ** SMDBE_OK -- Success.
  150. ** Anything else is an error. Look up more info about the
  151. ** error in the comments for the specific open() used.
  152. */
  153. int
  154. smdb_add_extension(full_name, max_full_name_len, db_name, extension)
  155. char *full_name;
  156. int max_full_name_len;
  157. char *db_name;
  158. char *extension;
  159. {
  160. int extension_len;
  161. int db_name_len;
  162. if (full_name == NULL || db_name == NULL || extension == NULL)
  163. return SMDBE_INVALID_PARAMETER;
  164. extension_len = strlen(extension);
  165. db_name_len = strlen(db_name);
  166. if (extension_len + db_name_len + 2 > max_full_name_len)
  167. return SMDBE_DB_NAME_TOO_LONG;
  168. if (db_name_len < extension_len ||
  169.     strcmp(&db_name[db_name_len - extension_len], extension) != 0)
  170. snprintf(full_name, max_full_name_len, "%s.%s", db_name,
  171.  extension);
  172. else
  173. (void) strlcpy(full_name, db_name, max_full_name_len);
  174. return SMDBE_OK;
  175. }
  176. /*
  177. **  SMDB_LOCK_FILE -- Locks the database file.
  178. **
  179. ** Locks the actual database file.
  180. **
  181. ** Parameters:
  182. ** lock_fd -- The resulting descriptor for the locked file.
  183. ** db_name -- The name of the database without extension.
  184. ** mode -- The open mode.
  185. ** sff -- Flags to safefile.
  186. ** extension -- The extension for the file.
  187. **
  188. ** Returns:
  189. ** SMDBE_OK -- Success, otherwise errno.
  190. */
  191. int
  192. smdb_lock_file(lock_fd, db_name, mode, sff, extension)
  193. int *lock_fd;
  194. char *db_name;
  195. int mode;
  196. int sff;
  197. char *extension;
  198. {
  199. int result;
  200. char file_name[SMDB_MAX_NAME_LEN];
  201. result = smdb_add_extension(file_name, SMDB_MAX_NAME_LEN, db_name,
  202.     extension);
  203. if (result != SMDBE_OK)
  204. return result;
  205. *lock_fd = safeopen(file_name, mode & ~O_TRUNC, 0644, sff);
  206. if (*lock_fd < 0)
  207. return errno;
  208. return SMDBE_OK;
  209. }
  210. /*
  211. **  SMDB_UNLOCK_FILE -- Unlocks a file
  212. **
  213. ** Unlocks a file.
  214. **
  215. ** Parameters:
  216. ** lock_fd -- The descriptor for the locked file.
  217. **
  218. ** Returns:
  219. ** SMDBE_OK -- Success, otherwise errno.
  220. */
  221. int
  222. smdb_unlock_file(lock_fd)
  223. int lock_fd;
  224. {
  225. int result;
  226. result = close(lock_fd);
  227. if (result != 0)
  228. return errno;
  229. return SMDBE_OK;
  230. }
  231. /*
  232. **  SMDB_SETUP_FILE -- Gets db file ready for use.
  233. **
  234. ** Makes sure permissions on file are safe and creates it if it
  235. ** doesn't exist.
  236. **
  237. ** Parameters:
  238. ** db_name -- The name of the database without extension.
  239. ** extension -- The extension.
  240. ** sff -- Flags to safefile.
  241. ** mode_mask -- Mode bits that must match.
  242. ** user_info -- Information on the user to use for file
  243. **     permissions.
  244. ** stat_info -- A place to put the stat info for the file.
  245. ** Returns:
  246. ** SMDBE_OK -- Success, otherwise errno.
  247. */
  248. int
  249. smdb_setup_file(db_name, extension, mode_mask, sff, user_info, stat_info)
  250. char *db_name;
  251. char *extension;
  252. int mode_mask;
  253. int sff;
  254. SMDB_USER_INFO *user_info;
  255. struct stat *stat_info;
  256. {
  257. int st;
  258. int result;
  259. char db_file_name[SMDB_MAX_NAME_LEN];
  260. result = smdb_add_extension(db_file_name, SMDB_MAX_NAME_LEN, db_name,
  261.     extension);
  262. if (result != SMDBE_OK)
  263. return result;
  264. st = safefile(db_file_name, user_info->smdbu_id,
  265.       user_info->smdbu_group_id, user_info->smdbu_name,
  266.       sff, mode_mask, stat_info);
  267. if (st != 0)
  268. return st;
  269. return SMDBE_OK;
  270. }
  271. /*
  272. **  SMDB_FILECHANGED -- Checks to see if a file changed.
  273. **
  274. ** Compares the passed in stat_info with a current stat on
  275. ** the passed in file descriptor. Check filechanged for
  276. ** return values.
  277. **
  278. ** Parameters:
  279. ** db_name -- The name of the database without extension.
  280. ** extension -- The extension.
  281. ** db_fd -- A file descriptor for the database file.
  282. ** stat_info -- An old stat_info.
  283. ** Returns:
  284. ** SMDBE_OK -- Success, otherwise errno.
  285. */
  286. int
  287. smdb_filechanged(db_name, extension, db_fd, stat_info)
  288. char *db_name;
  289. char *extension;
  290. int db_fd;
  291. struct stat *stat_info;
  292. {
  293. int result;
  294. char db_file_name[SMDB_MAX_NAME_LEN];
  295. result = smdb_add_extension(db_file_name, SMDB_MAX_NAME_LEN, db_name,
  296.     extension);
  297. if (result != SMDBE_OK)
  298. return result;
  299. result = filechanged(db_file_name, db_fd, stat_info);
  300. return result;
  301. }
  302. /*
  303. ** SMDB_PRINT_AVAILABLE_TYPES -- Prints the names of the available types.
  304. **
  305. ** Parameters:
  306. ** None
  307. **
  308. ** Returns:
  309. ** None
  310. */
  311. void
  312. smdb_print_available_types()
  313. {
  314. #ifdef NDBM
  315. printf("dbmn");
  316. #endif /* NDBM */
  317. #ifdef NEWDB
  318. printf("hashn");
  319. printf("btreen");
  320. #endif /* NEWDB */
  321. }
  322. /*
  323. ** SMDB_DB_DEFINITION -- Given a database type, return database definition
  324. **
  325. ** Reads though a structure making an association with the database
  326. ** type and the required cpp define from sendmail/README.
  327. ** List size is dynamic and must be NULL terminated.
  328. **
  329. ** Parameters:
  330. ** type -- The name of the database type.
  331. **
  332. ** Returns:
  333. ** definition for type, otherwise NULL.
  334. */
  335. typedef struct
  336. {
  337. SMDB_DBTYPE type;
  338. char *dbdef;
  339. } dbtype;
  340. static dbtype DatabaseDefs[] =
  341. {
  342. { SMDB_TYPE_HASH, "NEWDB" },
  343. { SMDB_TYPE_BTREE, "NEWDB" },
  344. { SMDB_TYPE_NDBM, "NDBM" },
  345. { NULL, "OOPS" }
  346. };
  347. char *
  348. smdb_db_definition(type)
  349. SMDB_DBTYPE type;
  350. {
  351. dbtype *ptr = DatabaseDefs;
  352. while (ptr != NULL && ptr->type != NULL)
  353. {
  354. if (strcmp(type, ptr->type) == 0)
  355. return ptr->dbdef;
  356. ptr++;
  357. }
  358. return NULL;
  359. }