globals.py 2.56 KB
Newer Older
Matt Traudt's avatar
Matt Traudt committed
1
import os
2
import time
3
import logging
4
from filelock import FileLock
Matt Traudt's avatar
Matt Traudt committed
5

6
log = logging.getLogger(__name__)
Matt Traudt's avatar
Matt Traudt committed
7
8
9

G_PKG_DIR = os.path.abspath(os.path.dirname(__file__))

10
11
12
# Minimum and maximum number of bytes a client is allowed to request from a
# server. If these are changed, a WIRE_PROTO_VER bump is required, which also
# happens to require an sbws major version bump.
13
14
15
16
17
18
19
20
#
# Note for smart people and people who pull out Wireshark: Even if the client
# requests 1 byte, that request and the 1 byte response will each be carried
# over the Internet in 514 byte Tor cells. Theoretically we could bump the
# minimum request size up to ~498 bytes, but I see no reason why we should.
# Trying to hit the maximum cell size just makes sbws server send more, us read
# more, and it runs the risk of standards changing underneath us and sbws
# suddenly creating more than one cell.
21
MIN_REQ_BYTES = 1
22
MAX_REQ_BYTES = 1 * 1024 * 1024 * 1024  # 1 GiB
23
SOCKET_TIMEOUT = 60  # seconds
24

Matt Traudt's avatar
Matt Traudt committed
25
26

def is_initted(d):
27
    if not os.path.isdir(d):
Matt Traudt's avatar
Matt Traudt committed
28
        return False
Matt Traudt's avatar
Matt Traudt committed
29
30
31
32
33
    conf_fnames = [os.path.join(d, 'config.ini'),
                   os.path.join(d, 'config.log.ini')]
    for fname in conf_fnames:
        if not os.path.exists(fname):
            return False
Matt Traudt's avatar
Matt Traudt committed
34
    return True
35
36


37
def fail_hard(*a, **kw):
Matt Traudt's avatar
Matt Traudt committed
38
    ''' Log something ... and then exit as fast as possible '''
Matt Traudt's avatar
Matt Traudt committed
39
    log.critical(*a, **kw)
40
    exit(1)
Matt Traudt's avatar
Matt Traudt committed
41
42


43
44
45
46
47
48
49
50
51
52
def time_now():
    '''
    Return the current time in seconds since 1970. This function exists to
    make testing easier

    :returns: Unix timestamp as a float
    '''
    return time.time()


53
54
55
56
57
58
59
60
61
62
63
64
65
66
def lock_directory(dname):
    '''
    Holds a lock on a file in **dname** so that other sbws processes/threads
    won't try to read/write while we are reading/writing in this directory.

    >>> with lock_directory(dname):
    >>>     # do things while you have the lock
    >>> # no longer have lock

    :param str dname: Name of directory we want to obtain a lock for
    :retrurns: the FileLock context manager for you to use in a with statement
    '''
    assert os.path.isdir(dname)
    return FileLock(os.path.join(dname, 'lockfile'))
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81


def touch_file(fname, times=None):
    '''
    If **fname** exists, update its last access and modified times to now. If
    **fname** does not exist, create it. If **times** are specified, pass them
    to os.utime for use.

    :param str fname: Name of file to update or create
    :param tuple times: 2-tuple of floats for access time and modified time
        respectively
    '''
    log.debug('Touching %s', fname)
    with open(fname, 'a') as fd:
        os.utime(fd.fileno(), times=times)