blob: 4396321e991d6effa0ebeb79b1db8d03020ead2d [file] [log] [blame]
Guido van Rossum8d12a1b1996-07-30 16:30:15 +00001"""Guess which db package to use to open a db file."""
2
3import struct
4
5def whichdb(filename):
6 """Guess which db package to use to open a db file.
7
8 Return values:
9
10 - None if the database file can't be read;
11 - empty string if the file can be read but can't be recognized
12 - the module name (e.g. "dbm" or "gdbm") if recognized.
13
14 Importing the given module may still fail, and opening the
15 database using that module may still fail.
16 """
17
18 # Check for dbm first -- this has a .pag and a .dir file
19 try:
Guido van Rossum45e2fbc1998-03-26 21:13:24 +000020 f = open(filename + ".pag", "rb")
21 f.close()
22 f = open(filename + ".dir", "rb")
23 f.close()
24 return "dbm"
Guido van Rossum8d12a1b1996-07-30 16:30:15 +000025 except IOError:
Guido van Rossum45e2fbc1998-03-26 21:13:24 +000026 pass
Guido van Rossum8d12a1b1996-07-30 16:30:15 +000027
Moshe Zadka7a4409c2000-07-29 05:31:40 +000028 # Check for dumbdbm next -- this has a .dir and and a .dat file
Thomas Wouters3027b152000-08-04 08:46:59 +000029 try:
Moshe Zadka7a4409c2000-07-29 05:31:40 +000030 f = open(filename + ".dat", "rb")
31 f.close()
32 f = open(filename + ".dir", "rb")
33 try:
34 if f.read(1) in ["'", '"']:
35 return "dumbdbm"
36 finally:
37 f.close()
38 except IOError:
39 pass
40
Guido van Rossum8d12a1b1996-07-30 16:30:15 +000041 # See if the file exists, return None if not
42 try:
Guido van Rossum45e2fbc1998-03-26 21:13:24 +000043 f = open(filename, "rb")
Guido van Rossum8d12a1b1996-07-30 16:30:15 +000044 except IOError:
Guido van Rossum45e2fbc1998-03-26 21:13:24 +000045 return None
Guido van Rossum8d12a1b1996-07-30 16:30:15 +000046
Guido van Rossumcf09a391999-06-08 13:13:16 +000047 # Read the start of the file -- the magic number
48 s16 = f.read(16)
Guido van Rossum8d12a1b1996-07-30 16:30:15 +000049 f.close()
Guido van Rossumcf09a391999-06-08 13:13:16 +000050 s = s16[0:4]
Guido van Rossum8d12a1b1996-07-30 16:30:15 +000051
52 # Return "" if not at least 4 bytes
53 if len(s) != 4:
Guido van Rossum45e2fbc1998-03-26 21:13:24 +000054 return ""
Guido van Rossum8d12a1b1996-07-30 16:30:15 +000055
56 # Convert to 4-byte int in native byte order -- return "" if impossible
57 try:
Guido van Rossum45e2fbc1998-03-26 21:13:24 +000058 (magic,) = struct.unpack("=l", s)
Guido van Rossum8d12a1b1996-07-30 16:30:15 +000059 except struct.error:
Guido van Rossum45e2fbc1998-03-26 21:13:24 +000060 return ""
Guido van Rossum8d12a1b1996-07-30 16:30:15 +000061
62 # Check for GNU dbm
63 if magic == 0x13579ace:
Guido van Rossum45e2fbc1998-03-26 21:13:24 +000064 return "gdbm"
Guido van Rossum8d12a1b1996-07-30 16:30:15 +000065
66 # Check for BSD hash
Guido van Rossumb86ba121998-04-28 15:41:03 +000067 if magic in (0x00061561, 0x61150600):
Guido van Rossum45e2fbc1998-03-26 21:13:24 +000068 return "dbhash"
Guido van Rossum8d12a1b1996-07-30 16:30:15 +000069
Guido van Rossumcf09a391999-06-08 13:13:16 +000070 # BSD hash v2 has a 12-byte NULL pad in front of the file type
71 try:
Fred Drake13a2c272000-02-10 17:17:14 +000072 (magic,) = struct.unpack("=l", s16[-4:])
Guido van Rossumcf09a391999-06-08 13:13:16 +000073 except struct.error:
74 return ""
75
76 # Check for BSD hash
77 if magic in (0x00061561, 0x61150600):
78 return "dbhash"
79
Guido van Rossum8d12a1b1996-07-30 16:30:15 +000080 # Unknown
81 return ""