1/*
2 * Copyright (c) 2016 ETH Zurich.
3 * All rights reserved.
4 *
5 * This file is distributed under the terms in the attached LICENSE file.
6 * If you do not find this file, copies can be found by writing to:
7 * ETH Zurich D-INFK, Universitaetstr. 6, CH-8092 Zurich. Attn: Systems Group.
8 */
9
10#include <barrelfish/barrelfish.h>
11#include <devif/queue_interface.h>
12#include "region.h"
13#include "dqi_debug.h"
14
15/*
16 * A region keeps track of the buffers that are currently allocated
17 * i.e. If two buffer is marked as allocated and it is reused before it
18 * is freed, the region will return an allocation error
19 *
20 * The datastructure to keep track of the allocation has a bucket for each
21 * 4K page. If a buffer starts in a certain page, the buffer will be added to
22 * the bucket of this page. Within a bucket there is a linked list. To allocated
23 * the buffer structures a slab allocator is used.
24 */
25/*
26static void print_list(struct buffer* b, uint32_t page_id, bool insert) {
27
28    printf("########################### \n");
29    struct buffer* buf = b;
30    for (int i =0; i < 9; i++) {
31        if (buf) {
32            if (insert) {
33                printf("ins page_id %d, bid %d, baddr %p, baddr->next %p \n", page_id,
34                       buf->id, buf, buf->next);
35            } else {
36                printf("del page_id %d, bid %d, baddr %p, baddr->next %p \n", page_id,
37                       buf->id, buf, buf->next);
38            }
39            buf = buf->next;
40        } else {
41            break;
42        }
43    }
44    printf("############################## \n");
45}
46*/
47/**
48 * @brief initialized a region from which only fixed size buffers are used
49 *
50 * @param region                Return pointer to the region
51 * @param region_id             The ID of the region,
52 * @param cap                   Capability of the memory region
53 *
54 * @returns error on failure or SYS_ERR_OK on success
55 */
56
57errval_t region_init(struct region** region,
58                     regionid_t region_id,
59                     struct capref* cap)
60{
61    errval_t err;
62    struct frame_identity id;
63
64    struct region* tmp = calloc(1, sizeof(struct region));
65    if (tmp == NULL) {
66        return LIB_ERR_MALLOC_FAIL;
67    }
68
69    tmp->id = region_id;
70    tmp->cap = cap;
71
72    err = invoke_frame_identify(*cap, &id);
73    if (err_is_fail(err)) {
74        return err;
75    }
76
77    tmp->base_addr = id.base;
78    tmp->len = id.bytes;
79
80    *region = tmp;
81
82    DQI_DEBUG_REGION("Initialize Region size=%ld addr=%16lx\n",
83              tmp->len, tmp->base_addr);
84
85    return SYS_ERR_OK;
86}
87
88
89/**
90 * @brief free up a region
91 *
92 * @param region                The region to free up
93 *
94 * @returns error on failure or SYS_ERR_OK on success
95 */
96errval_t region_destroy(struct region* region)
97{
98    free(region);
99    return SYS_ERR_OK;
100}
101
102