# libpmp ## pmp_heap.c ``` c void pmp_mmap(unsigned int start, unsigned int end, unsigned char privilege, int v_pmp_id); ``` * 重新整理这个链表,如果有重叠就进行拆分,保证插入`[start, end]后`,最后链表中的每个节点存储的区间都没有重叠。 * 遍历原来的链表,找到所有和`[start, end]`有重叠的区间`[si, ei]`,然后切分成若干个小区间(切分方法如下),每个小区间存成一个链表节点。注意,如果两个完全相同的区间优先级不同,那么它们将会作为两个节点(两个节点只有优先级不同)同时存在链表中。 * 切分的例子:![](https://i.imgur.com/lanVJg6.png) * 切分完之后,需要更新PMP entry,更新的方法如下: * 遍历所有的PMP entry,对于某一个PMP entry管理的区间,如果这个区间和`[start, end]` 有交集,那么分为三种情况,假设PMP entry管理的区间是`[s, e]` * 如果`[start, end]`包含了`[s, e]`,那么`[s, e]`一定和上面切分后的某个小区间范围相同。这时候就比较两者的优先级,如果PMP entry的优先级低,就需要refresh。 * 如果`[start, end]`和`[s, e]`不是包含,只是有交集,那么二者的交集部分一定和上面切分后的某个小区间范围相同,这时候也是比较这两个小区间的优先级,处理方法和上面相同。 例子: ``` c void pmp_free(v_id) ``` * 遍历链表,如果某个节点的id和传入的id相同,直接从链表中删除。 * 遍历PMP entry,如果PMP entry中的区间id和传入的id相同,就直接把这个PMP entry抹除。 ## exception.c ``` c pmp_exception_handler(void * addr); ``` * 异常处理程序,当用户访问一个地址时,如果PMP规定这个地址访问不合法,就会调用异常处理函数。 * 如果这个地址在PMP区间里,不用管。 * 如果不在,就把这个地址当作参数,在链表里,找到优先级最高的区间,然后放到物理的PMP寄存器中。 pmp_util.c pmp_debug.c