Fork us on GitHub Follow us on Facebook Follow us on Twitter

Changeset 8049b79 in mainline


Ignore:
Timestamp:
2013-09-12T19:30:25Z (8 years ago)
Author:
Jakub Jermar <jakub@…>
Branches:
lfn, master
Children:
7de1988c
Parents:
46eb2c4
Message:

Apply PIO window when parsing HW resources.

  • Each parsed IO and memory range will have both absolute and PIO window relative addresses computed.
  • Provide pio_enable_range() variant of pio_enable() working with addr_range_t.
Location:
uspace/lib/c
Files:
4 edited

Legend:

Unmodified
Added
Removed
  • uspace/lib/c/generic/ddi.c

    r46eb2c4 r8049b79  
    4242#include <ddi.h>
    4343#include <libarch/ddi.h>
     44#include <device/hw_res.h>
     45#include <device/hw_res_parsed.h>
     46#include <device/pio_window.h>
    4447#include <libc.h>
    4548#include <task.h>
     
    136139}
    137140
    138 /** Enable PIO for specified HW resource.
     141/** Enable PIO for specified address range.
     142 *
     143 * @param range I/O range to be enable.
     144 * @param virt  Virtual address for application's PIO operations.
     145 */
     146int pio_enable_range(addr_range_t *range, void **virt)
     147{
     148        return pio_enable(RNGABSPTR(*range), RNGSZ(*range), virt);
     149}
     150
     151/** Enable PIO for specified HW resource wrt. to the PIO window.
    139152 *
    140153 * @param win      PIO window. May be NULL if the resources are known to be
  • uspace/lib/c/generic/device/hw_res_parsed.c

    r46eb2c4 r8049b79  
    8080}
    8181
     82static uint64_t absolutize(uint64_t addr, bool relative, uint64_t base)
     83{
     84        if (!relative)
     85                return addr;
     86        else
     87                return addr + base;
     88}
     89
     90static uint64_t relativize(uint64_t addr, bool relative, uint64_t base)
     91{
     92        if (relative)
     93                return addr;
     94        else
     95                return addr - base;
     96}
     97
    8298static void hw_res_parse_add_io_range(hw_res_list_parsed_t *out,
    83     const hw_resource_t *res, int flags)
    84 {
     99    const pio_window_t *win, const hw_resource_t *res, int flags)
     100{
     101        endianness_t endianness;
     102        uint64_t absolute;
     103        uint64_t relative;
     104        size_t size;
     105
    85106        assert(res && (res->type == IO_RANGE));
    86107       
    87         uint64_t address = res->res.io_range.address;
    88         endianness_t endianness = res->res.io_range.endianness;
    89         size_t size = res->res.io_range.size;
     108        absolute = absolutize(res->res.io_range.address,
     109            res->res.io_range.relative, win->io.base);
     110        relative = relativize(res->res.io_range.address,
     111            res->res.io_range.relative, win->io.base);
     112        size = res->res.io_range.size;
     113        endianness = res->res.io_range.endianness;
    90114       
    91115        if ((size == 0) && (!(flags & HW_RES_KEEP_ZERO_AREA)))
     
    97121        if (!keep_duplicit) {
    98122                for (size_t i = 0; i < count; i++) {
    99                         uint64_t s_address = out->io_ranges.ranges[i].address;
    100                         size_t s_size = out->io_ranges.ranges[i].size;
     123                        uint64_t s_address;
     124                        size_t s_size;
     125
     126                        s_address = RNGABS(out->io_ranges.ranges[i]);
     127                        s_size = RNGSZ(out->io_ranges.ranges[i]);
    101128                       
    102                         if ((address == s_address) && (size == s_size))
    103                                 return;
    104                 }
    105         }
    106        
    107         out->io_ranges.ranges[count].address = address;
     129                        if ((absolute == s_address) && (size == s_size))
     130                                return;
     131                }
     132        }
     133       
     134        RNGABS(out->io_ranges.ranges[count]) = absolute;
     135        RNGREL(out->io_ranges.ranges[count]) = relative;
     136        RNGSZ(out->io_ranges.ranges[count]) = size;
    108137        out->io_ranges.ranges[count].endianness = endianness;
    109         out->io_ranges.ranges[count].size = size;
    110138        out->io_ranges.count++;
    111139}
    112140
    113141static void hw_res_parse_add_mem_range(hw_res_list_parsed_t *out,
    114     const hw_resource_t *res, int flags)
    115 {
     142    const pio_window_t *win, const hw_resource_t *res, int flags)
     143{
     144        endianness_t endianness;
     145        uint64_t absolute;
     146        uint64_t relative;
     147        size_t size;
     148       
    116149        assert(res && (res->type == MEM_RANGE));
    117150       
    118         uint64_t address = res->res.mem_range.address;
    119         endianness_t endianness = res->res.mem_range.endianness;
    120         size_t size = res->res.mem_range.size;
     151        absolute = absolutize(res->res.mem_range.address,
     152            res->res.mem_range.relative, win->mem.base);
     153        relative = relativize(res->res.mem_range.address,
     154            res->res.mem_range.relative, win->mem.base);
     155        size = res->res.mem_range.size;
     156        endianness = res->res.mem_range.endianness;
    121157       
    122158        if ((size == 0) && (!(flags & HW_RES_KEEP_ZERO_AREA)))
     
    128164        if (!keep_duplicit) {
    129165                for (size_t i = 0; i < count; ++i) {
    130                         uint64_t s_address = out->mem_ranges.ranges[i].address;
    131                         size_t s_size = out->mem_ranges.ranges[i].size;
     166                        uint64_t s_address;
     167                        size_t s_size;
     168
     169                        s_address = RNGABS(out->mem_ranges.ranges[i]);;
     170                        s_size = RNGSZ(out->mem_ranges.ranges[i]);
    132171                       
    133                         if ((address == s_address) && (size == s_size))
    134                                 return;
    135                 }
    136         }
    137        
    138         out->mem_ranges.ranges[count].address = address;
     172                        if ((absolute == s_address) && (size == s_size))
     173                                return;
     174                }
     175        }
     176       
     177        RNGABS(out->mem_ranges.ranges[count]) = absolute;
     178        RNGREL(out->mem_ranges.ranges[count]) = relative;
     179        RNGSZ(out->mem_ranges.ranges[count]) = size;
    139180        out->mem_ranges.ranges[count].endianness = endianness;
    140         out->mem_ranges.ranges[count].size = size;
    141181        out->mem_ranges.count++;
    142182}
     
    144184/** Parse list of hardware resources
    145185 *
    146  * @param      hw_resources Original structure resource
    147  * @param[out] out          Output parsed resources
    148  * @param      flags        Flags of the parsing.
    149  *                          HW_RES_KEEP_ZERO_AREA for keeping
    150  *                          zero-size areas, HW_RES_KEEP_DUPLICITIES
    151  *                          for keep duplicit areas
     186 * @param      win          PIO window.
     187 * @param      res          Original structure resource.
     188 * @param[out] out          Output parsed resources.
     189 * @param      flags        Flags of the parsing:
     190 *                          HW_RES_KEEP_ZERO_AREA for keeping zero-size areas,
     191 *                          HW_RES_KEEP_DUPLICITIES to keep duplicit areas.
    152192 *
    153193 * @return EOK if succeed, error code otherwise.
    154194 *
    155195 */
    156 int hw_res_list_parse(const hw_resource_list_t *hw_resources,
    157     hw_res_list_parsed_t *out, int flags)
    158 {
    159         if ((!hw_resources) || (!out))
     196int hw_res_list_parse(const pio_window_t *win,
     197    const hw_resource_list_t *res, hw_res_list_parsed_t *out, int flags)
     198{
     199        if (!res || !out)
    160200                return EINVAL;
    161201       
    162         size_t res_count = hw_resources->count;
     202        size_t res_count = res->count;
    163203        hw_res_list_parsed_clean(out);
    164204       
     
    174214       
    175215        for (size_t i = 0; i < res_count; ++i) {
    176                 const hw_resource_t *resource = &(hw_resources->resources[i]);
     216                const hw_resource_t *resource = &res->resources[i];
    177217               
    178218                switch (resource->type) {
     
    181221                        break;
    182222                case IO_RANGE:
    183                         hw_res_parse_add_io_range(out, resource, flags);
     223                        hw_res_parse_add_io_range(out, win, resource, flags);
    184224                        break;
    185225                case MEM_RANGE:
    186                         hw_res_parse_add_mem_range(out, resource, flags);
     226                        hw_res_parse_add_mem_range(out, win, resource, flags);
    187227                        break;
    188228                case DMA_CHANNEL_8:
     
    216256    hw_res_list_parsed_t *hw_res_parsed, int flags)
    217257{
     258        pio_window_t pio_window;
     259        int rc;
     260
    218261        if (!hw_res_parsed)
    219262                return EBADMEM;
     
    222265        hw_res_list_parsed_clean(hw_res_parsed);
    223266        memset(&hw_resources, 0, sizeof(hw_resource_list_t));
    224        
    225         int rc = hw_res_get_resource_list(sess, &hw_resources);
     267
     268        rc = pio_window_get(sess, &pio_window);
     269        if (rc != EOK)
     270                return rc;
     271       
     272        rc = hw_res_get_resource_list(sess, &hw_resources);
    226273        if (rc != EOK)
    227274                return rc;
    228        
    229         rc = hw_res_list_parse(&hw_resources, hw_res_parsed, flags);
     275
     276        rc = hw_res_list_parse(&pio_window, &hw_resources, hw_res_parsed,
     277            flags);
    230278        hw_res_clean_resource_list(&hw_resources);
    231279       
  • uspace/lib/c/include/ddi.h

    r46eb2c4 r8049b79  
    4141#include <abi/ddi/irq.h>
    4242#include <device/hw_res.h>
     43#include <device/hw_res_parsed.h>
    4344#include <device/pio_window.h>
    4445#include <task.h>
     
    5758extern int dmamem_unmap_anonymous(void *);
    5859
     60extern int pio_enable_range(addr_range_t *, void **);
    5961extern int pio_enable_resource(pio_window_t *, hw_resource_t *, void **);
    6062extern int pio_enable(void *, size_t, void **);
  • uspace/lib/c/include/device/hw_res_parsed.h

    r46eb2c4 r8049b79  
    3737
    3838#include <device/hw_res.h>
     39#include <device/pio_window.h>
    3940#include <str.h>
    4041
     
    4546#define HW_RES_KEEP_DUPLICIT   0x2
    4647
     48
     49#define RNGABS(rng)     (rng).address.absolute
     50#define RNGREL(rng)     (rng).address.relative
     51#define RNGSZ(rng)      (rng).size
     52
     53#define RNGABSPTR(rng)  ((void *) ((uintptr_t) RNGABS((rng))))
     54
     55typedef struct address64 {
     56        /** Aboslute address. */
     57        uint64_t absolute;
     58        /** PIO window base relative address. */
     59        uint64_t relative;
     60} address64_t;
     61
    4762/** Address range structure */
    4863typedef struct addr_range {
    4964        /** Start address */
    50         uint64_t address;
    51        
    52         /** Endianness */
    53         endianness_t endianness;
     65        address64_t address;
    5466       
    5567        /** Area size */
    5668        size_t size;
     69
     70        /** Endianness */
     71        endianness_t endianness;
    5772} addr_range_t;
    5873
     
    139154}
    140155
    141 extern int hw_res_list_parse(const hw_resource_list_t *,
     156extern int hw_res_list_parse(const pio_window_t *, const hw_resource_list_t *,
    142157    hw_res_list_parsed_t *, int);
    143158extern int hw_res_get_list_parsed(async_sess_t *, hw_res_list_parsed_t *, int);
Note: See TracChangeset for help on using the changeset viewer.