0
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
| | #! /bin/env python
import bsddb
from optparse import OptionParser
import os
import os.path
import re
import platform
__doc__ = """There is no file spacification for uno_packages.db
and uno_packages.pmap but you can find its implementation in
main/desktop/source/deployment/dp_persmap.cxx of the source code. """
def get_items(packages):
""" Open Berkeley database file and read its content.
# Format of uno_packages.db
# Berkeley detabase
# Ignore white spaces in key and value
# key: 0xFF EXTENSION_ID
# value: TEMP_NAME 0xFF PACKAGE_NAME 0xFF PACKAGE_MIME_TYPE 0xFF VERSION 0xFF 0
# The last value is always zero in value because of it is not used anymore.
"""
items = {}
d = bsddb.hashopen(packages + ".db", "r")
for k, v in d.iteritems():
items[k] = v
d.close()
return items
def write_pmap(packages, items):
""" Write to pmap file.
# Format of uno_packages.pmap
# file header: Pmp1
# Ignore white space in the body.
# body: key \n value \n
# file footer: \n
# The 00 ... 0F are replaced with %0 ... %F and
# % is replaced with %% in key and value.
"""
magic = "Pmp1"
regexp = re.compile("(\x00|\x01|\x02|\x03|\x04|\x05|\x06|\x07|\x08|\x09|\x0a|\x0b|\x0c|\x0d|\x0e|\x0f|%)")
def encode(m):
# 00 ... 0F -> %0 ... %F, % -> %%
c = m.group(0)
if c == "%":
return "%%"
else:
n = ord(c)
if n < 0x09:
return "%%%s" % chr(0x30 + n)
else:
return "%%%s" % chr(0x37 + n)
lines = []
for k, v in items.iteritems():
lines.append(regexp.sub(encode, k))
lines.append(regexp.sub(encode, v))
lines.append("\n")
f = open(packages + ".pmap", "w")
f.write(magic)
f.write("\n".join(lines))
f.flush()
f.close()
def main():
""" Tries to convert uno_packages.db to pmap. """
USER_KEY = "user"
if os.sep == "/":
data_dir = os.path.join("~", ".openoffice.org")
elif platform.system() == "Windows":
release = platform.release()
if release == "XP" or release == "2000":
data_dir = os.path.join("~", "Application Data", "OpenOffice.org")
else:
data_dir = os.path.join("~", "AppData", "OpenOffice.org")
parser = OptionParser()
parser.add_option("-u", dest=USER_KEY,
help="Data directory of the office. Default: %s" % data_dir)
parser.set_default(USER_KEY, data_dir)
options, args = parser.parse_args()
packages_dir = os.path.join(
os.path.expanduser(getattr(options, USER_KEY)),
"3", "user",
"uno_packages", "cache")
# check user directory is exist
if not os.path.exists(packages_dir):
print("Error: %s is not found." % packages_dir)
return
packages_path = os.path.join(packages_dir, "uno_packages")
items = get_items(packages_path)
write_pmap(packages_path, items)
if __name__ == "__main__":
main()
|