DataWorks
Database Library/Client
Loading...
Searching...
No Matches
database.c
1/* $Id: database.c 97 2024-05-23 17:15:24Z nishi $ */
2/* --- START LICENSE --- */
3/* -------------------------------------------------------------------------- */
4/* Copyright (c) 2024 Crabware. */
5/* Redistribution and use in source and binary forms, with or without modific */
6/* ation, are permitted provided that the following conditions are met: */
7/* 1. Redistributions of source code must retain the above copyright noti */
8/* ce, this list of conditions and the following disclaimer. */
9/* 2. Redistributions in binary form must reproduce the above copyright n */
10/* otice, this list of conditions and the following disclaimer in the documen */
11/* tation and/or other materials provided with the distribution. */
12/* 3. Neither the name of the copyright holder nor the names of its contr */
13/* ibutors may be used to endorse or promote products derived from this softw */
14/* are without specific prior written permission. */
15/* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS */
16/* " AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, TH */
17/* E IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPO */
18/* SE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS */
19/* BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CON */
20/* SEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITU */
21/* TE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPT */
22/* ION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, S */
23/* TRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN AN */
24/* Y WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY */
25/* OF SUCH DAMAGE. */
26/* -------------------------------------------------------------------------- */
27/* --- END LICENSE --- */
28
29#include "dw_database.h"
30
31#include "dw_util.h"
32
33#include <stdint.h>
34#include <stdio.h>
35#include <stdlib.h>
36#include <string.h>
37#include <time.h>
38
39const char sig[3] = {0x7f, 'D', 'W'};
40
41#ifdef M_I86
42#define BUFSIZE 128
43#endif
44
45int dataworks_database_create(const char* fname) {
46 FILE* f = fopen(fname, "wb");
47 if(f == NULL) {
48 return 1;
49 }
50#ifdef BUFSIZE
51 uint8_t nul[BUFSIZE];
52#else
53 uint8_t nul[4096];
54#endif
55 int i;
56 fwrite(sig, 1, 3, f);
57 nul[0] = 0;
58 nul[1] = 1;
59 fwrite(nul, 1, 2, f);
60 int64_t t = time(NULL);
61 __dw_big_endian(t, int64_t, fwrite(__converted_ptr, 1, 8, f));
62 for(i = 0; i < sizeof(nul); i++) nul[i] = 0;
63 for(i = 0; i < 256; i++) {
64 fwrite(nul, 1, 1, f);
65 fwrite(nul, 1, 8, f);
66 fwrite(nul, 1, 1, f);
67 int j;
68#ifdef BUFSIZE
69 for(j = 0; j < 256 / BUFSIZE; j++) {
70 fwrite(nul, 1, BUFSIZE, f);
71 }
72 for(j = 0; j < 4096 / BUFSIZE; j++) {
73 fwrite(nul, 1, BUFSIZE, f);
74 }
75#else
76 fwrite(nul, 1, 256, f);
77 fwrite(nul, 1, 4096, f);
78#endif
79 }
80 fclose(f);
81 return 0;
82}
83
84void dataworks_database_close(struct dataworks_db* db) {
85 if(db->fp != NULL) fclose(db->fp);
86 free(db);
87}
88
89struct dataworks_db* dataworks_database_open(const char* fname) {
90 struct dataworks_db* db = malloc(sizeof(*db));
91 db->error = false;
92 db->fp = NULL;
93 FILE* fp = fopen(fname, "rb+");
94 if(fp == NULL) {
95 db->error = true;
97 return db;
98 }
99 fseek(fp, 0, SEEK_SET);
100 char readsig[sizeof(sig)];
101 fread(readsig, 1, sizeof(sig), fp);
102 if(memcmp(readsig, sig, sizeof(sig)) != 0) {
103 db->error = true;
105 return db;
106 }
107 __dw_lockfile(fp);
108 char ptrver[8];
109 fread(ptrver, 1, 2, fp);
110 uint16_t be_ver = *(uint16_t*)(char*)ptrver;
111 uint16_t ver;
112 __dw_native_endian(be_ver, uint16_t, ver = __converted);
113 fread(ptrver, 1, 8, fp);
114 uint64_t be_mtime = *(uint64_t*)(char*)ptrver;
115 uint64_t mtime;
116 __dw_native_endian(be_mtime, uint64_t, mtime = __converted);
117 __dw_unlockfile(fp);
118 if(ver == 1) {
119 db->fp = fp;
120 db->version = ver;
121 db->mtime = mtime;
122 return db;
123 } else {
124 fclose(fp);
125 db->error = true;
127 return db;
128 }
129}
130
132
133uint64_t dataworks_database_get_mtime(struct dataworks_db* db) { return db->mtime; }
134
136
137const char* dw_errors[] = {"Success", "Used already", "File open fail", "Invalid signature", "Invalid version", "Parser returned NULL", "Cannot call non-method", "Unknown method", "Insufficient arguments"};
138
139const char* dataworks_database_strerror(int n) { return dw_errors[n]; }
140
142 __dw_lockfile(db->fp);
143 fseek(db->fp, 3 + 2, SEEK_SET);
144 int64_t t = time(NULL);
145 __dw_big_endian(t, int64_t, fwrite(__converted_ptr, 1, 8, db->fp));
146 __dw_unlockfile(db->fp);
147}
DataWorks database.
uint64_t dataworks_database_get_mtime(struct dataworks_db *db)
Get the last modified time of the database.
Definition database.c:133
void dataworks_database_update_mtime(struct dataworks_db *db)
Update mtime.
Definition database.c:141
const char * dataworks_database_strerror(int n)
Converts error number to a string.
Definition database.c:139
int dataworks_database_get_error_number(struct dataworks_db *db)
Get the error number of the database.
Definition database.c:135
@ DW_ERR_INVALID_SIGNATURE
Invalid signature.
Definition dw_database.h:88
@ DW_ERR_INVALID_VERSION
Invalid version.
Definition dw_database.h:95
@ DW_ERR_FAIL_FOPEN
File open fail.
Definition dw_database.h:81
struct dataworks_db * dataworks_database_open(const char *fname)
Opens the database.
Definition database.c:89
int dataworks_database_get_version(struct dataworks_db *db)
Get the version of the database.
Definition database.c:131
DataWorks utils.
Database struct.
bool error
True if this is an error.
int errnum
Error number.
uint64_t mtime
Last modified time of the database.
FILE * fp
File pointer to the database file.
uint16_t version
Version of the database.