#!/usr/bin/env python # -*- coding: utf-8 -*- import os import sys from sharedlibrary import GenericLibrary from ctypes import * # forward declaration class StructRingFSFlashPartition(Structure): pass op_sector_erase_t = CFUNCTYPE(c_int, POINTER(StructRingFSFlashPartition), c_int) op_program_t = CFUNCTYPE(c_ssize_t, POINTER(StructRingFSFlashPartition), c_int, c_void_p, c_size_t) op_read_t = CFUNCTYPE(c_ssize_t, POINTER(StructRingFSFlashPartition), c_int, c_void_p, c_size_t) StructRingFSFlashPartition._fields_ = [ ('sector_size', c_int), ('sector_offset', c_int), ('sector_count', c_int), ('sector_erase', op_sector_erase_t), ('program', op_program_t), ('read', op_read_t), ] class StructRingFSLoc(Structure): _fields_ = [ ('sector', c_int), ('slot', c_int), ] class StructRingFS(Structure): _fields_ = [ ('flash', POINTER(StructRingFSFlashPartition)), ('version', c_uint32), ('object_size', c_int), ('slots_per_sector', c_int), ('read', StructRingFSLoc), ('write', StructRingFSLoc), ('cursor', StructRingFSLoc), ] class libringfs(GenericLibrary): dllname = './ringfs.so' functions = [ ['ringfs_init', [POINTER(StructRingFS), POINTER(StructRingFSFlashPartition), c_uint32, c_int], c_int], ['ringfs_format', [POINTER(StructRingFS)], c_int], ['ringfs_scan', [POINTER(StructRingFS)], c_int], ['ringfs_capacity', [POINTER(StructRingFS)], c_int], ['ringfs_count_estimate', [POINTER(StructRingFS)], c_int], ['ringfs_count_exact', [POINTER(StructRingFS)], c_int], ['ringfs_append', [POINTER(StructRingFS), c_void_p], c_int], ['ringfs_fetch', [POINTER(StructRingFS), c_void_p], c_int], ['ringfs_discard', [POINTER(StructRingFS)], c_int], ['ringfs_rewind', [POINTER(StructRingFS)], c_int], ['ringfs_dump', [c_void_p, POINTER(StructRingFS)], None], ] class RingFSFlashPartition(object): def __init__(self, sector_size, sector_offset, sector_count, sector_erase, program, read): def op_sector_erase(flash, address): sector_erase(flash, address) return 0 def op_program(flash, address, data, size): program(flash, address, string_at(data, size)) return size def op_read(flash, address, buf, size): data = read(flash, address, size) memmove(buf, data, size) return size self.struct = StructRingFSFlashPartition(sector_size, sector_offset, sector_count, op_sector_erase_t(op_sector_erase), op_program_t(op_program), op_read_t(op_read)) class RingFS(object): def __init__(self, flash, version, object_size): self.libringfs = libringfs() self.ringfs = StructRingFS() self.flash = flash.struct self.libringfs.ringfs_init(byref(self.ringfs), byref(self.flash), version, object_size) self.object_size = object_size def format(self): self.libringfs.ringfs_format(byref(self.ringfs)) def scan(self): return self.libringfs.ringfs_scan(byref(self.ringfs)) def capacity(self): return self.libringfs.ringfs_capacity(byref(self.ringfs)) def count_estimate(self): return self.libringfs.ringfs_count_estimate(byref(self.ringfs)) def count_exact(self): return self.libringfs.ringfs_count_exact(byref(self.ringfs)) def append(self, obj): self.libringfs.ringfs_append(byref(self.ringfs), obj) def fetch(self): obj = create_string_buffer(self.object_size) self.libringfs.ringfs_append(byref(self.ringfs), obj) return obj.raw def discard(self): self.libringfs.ringfs_discard(byref(self.ringfs)) def rewind(self): self.libringfs.ringfs_rewind(byref(self.ringfs)) def dump(self): import ctypes ctypes.pythonapi.PyFile_AsFile.argtypes= [ ctypes.py_object ] ctypes.pythonapi.PyFile_AsFile.restype= ctypes.c_void_p cstdout = ctypes.pythonapi.PyFile_AsFile(sys.stdout) self.libringfs.ringfs_dump(cstdout, byref(self.ringfs)) __all__ = [ 'StructRingFSFlashPartition', 'RingFS', ]