Ignore:
Timestamp:
Jan 5, 2022, 10:39:39 AM (4 years ago)
Author:
caparsons <caparson@…>
Branches:
ADT, ast-experimental, enum, forall-pointer-decay, master, pthread-emulation, qualifiedEnum
Children:
0ac728b
Parents:
e2853eb (diff), 6111f1f (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the (diff) links above to see all the changes relative to each parent.
Message:

Merge branch 'master' of plg.uwaterloo.ca:software/cfa/cfa-cc

File:
1 edited

Legend:

Unmodified
Added
Removed
  • libcfa/src/device/cpu.cfa

    re2853eb r6c53a93  
    3030        #include <fcntl.h>
    3131}
     32
     33#include "algorithms/range_iterator.hfa"
    3234
    3335// search a string for character 'character' but looking atmost at len
     
    135137                count++;
    136138        }
    137         iterate_dir(path, lambda);
     139        int ret = iterate_dir(path, lambda);
     140        if(ret == ENOTDIR) return 0;
    138141
    139142        /* paranoid */ verifyf(count == max + 1, "Inconsistent %s count, counted %d, but max %s was %d", prefix, count, prefix, (int)max);
     
    143146
    144147// Count number of cpus in the system
    145 static int count_cpus(void) {
     148static [int, const char *] count_cpus(void) {
    146149        const char * fpath = "/sys/devices/system/cpu/online";
    147150        int fd = open(fpath, 0, O_RDONLY);
     
    159162
    160163        const char * _;
    161         int cnt = read_width(buff, r - 1, &_);
    162         /* paranoid */ verify(cnt == count_prefix_dirs("/sys/devices/system/cpu", "cpu"));
    163         return cnt;
     164        return [read_width(buff, r - 1, &_), strndup(buff, r - 1)];
    164165}
    165166
     
    226227
    227228struct raw_cache_instance {
    228         idx_range_t range;
    229         unsigned width;
    230         unsigned char level;
     229        idx_range_t range;      // A text description of the cpus covered
     230        unsigned width;         // The number of cpus covered
     231        unsigned char level;    // the cache level
    231232        // FIXME add at least size and type
    232233};
     
    235236static void ^?{}(raw_cache_instance & this) { free(this.range);}
    236237
    237 raw_cache_instance ** build_raw_cache_table(unsigned cpus, unsigned idxs, unsigned cache_levels)
     238// Returns a 2D array of instances of size [cpu count][cache levels]
     239// where cache level doesn't include instruction caches
     240raw_cache_instance ** build_raw_cache_table(unsigned cpus_c, idx_range_t cpus, unsigned idxs, unsigned cache_levels)
    238241{
    239         raw_cache_instance ** raw = alloc(cpus);
    240         for(i; cpus) {
     242        raw_cache_instance ** raw = alloc(cpus_c, '\0'`fill);
     243
     244        RangeIter rc = { cpus };
     245        while(moveNext(rc)) {
     246                unsigned i = rc.com;
    241247                raw[i] = alloc(cache_levels);
    242248                void addcache(unsigned fidx, unsigned char level, idx_range_t range, size_t len) {
     
    263269
    264270// returns an allocate list of all the different distinct last level caches
    265 static [*llc_map_t, size_t cnt] distinct_llcs(unsigned cpus, unsigned llc_idx, raw_cache_instance ** raw) {
     271static [*llc_map_t, size_t cnt] distinct_llcs(idx_range_t cpus, unsigned llc_idx, raw_cache_instance ** raw) {
    266272        // Allocate at least one element
    267273        llc_map_t* ranges = alloc();
    268274        size_t range_cnt = 1;
    269275
     276        RangeIter rc = { cpus };
     277        __attribute__((unused)) bool ret =
     278        moveNext(rc);
     279        /* paranoid */ verify( ret );
     280        /* paranoid */ verify( rc.com >= 0 );
     281
    270282        // Initialize with element 0
    271         ranges->raw = &raw[0][llc_idx];
     283        ranges->raw = &raw[rc.com][llc_idx];
    272284        ranges->count = 0;
    273285        ranges->start = -1u;
    274286
    275287        // Go over all other cpus
    276         CPU_LOOP: for(i; 1~cpus) {
     288        CPU_LOOP: while(moveNext(rc)) {
     289                unsigned i = rc.com;
    277290                // Check if the range is already there
    278291                raw_cache_instance * candidate = &raw[i][llc_idx];
     
    304317}
    305318
    306 static [[]cpu_pairing_t] get_cpu_pairings(unsigned cpus, raw_cache_instance ** raw, llc_map_t * maps, size_t map_cnt) {
    307         cpu_pairing_t * pairings = alloc(cpus);
    308 
    309         CPU_LOOP: for(i; cpus) {
     319static [[]cpu_pairing_t] get_cpu_pairings(unsigned cpus_c, idx_range_t cpus, raw_cache_instance ** raw, llc_map_t * maps, size_t map_cnt) {
     320        cpu_pairing_t * pairings = alloc(cpus_c);
     321
     322        RangeIter rc = { cpus };
     323        CPU_LOOP: while(moveNext(rc)) {
     324                unsigned i = rc.com;
    310325                pairings[i].cpu = i;
    311326                idx_range_t want = raw[i][0].range;
     
    327342extern "C" {
    328343        void __cfaabi_device_startup( void ) {
    329                 int cpus = count_cpus();
     344                int cpus_c;
     345                const char * cpus;
     346                [cpus_c, cpus] = count_cpus();
     347                #if defined(__CFA_WITH_VERIFY__)
     348                // Verify that the mapping is self consistant.
     349                {
     350                        RangeIter rc = { cpus };
     351                        while(moveNext(rc)) {
     352                                unsigned i = rc.com;
     353                                verify(cpus_c > i);
     354                        }
     355                }
     356                #endif
     357
    330358                int idxs = count_cache_indexes();
    331359
     
    333361                unsigned cache_levels = 0;
    334362                unsigned llc = 0;
    335                 {
     363                if (idxs != 0) {
    336364                        unsigned char prev = -1u;
    337365                        void first(unsigned idx, unsigned char level, const char * map, size_t len) {
     
    345373
    346374                // Read in raw data
    347                 raw_cache_instance ** raw = build_raw_cache_table(cpus, idxs, cache_levels);
     375                raw_cache_instance ** raw = build_raw_cache_table(cpus_c, cpus, idxs, cache_levels);
    348376
    349377                // Find number of distinct cache instances
     
    362390                                width2 += maps[i].raw->width;
    363391                        }
    364                         verify(width1 == cpus);
    365                         verify(width2 == cpus);
     392                        verify(width1 == cpus_c);
     393                        verify(width2 == cpus_c);
    366394                }
    367395                #endif
    368396
    369397                // Get mappings from cpu to cache instance
    370                 cpu_pairing_t * pairings = get_cpu_pairings(cpus, raw, maps, map_cnt);
     398                cpu_pairing_t * pairings = get_cpu_pairings(cpus_c, cpus, raw, maps, map_cnt);
    371399
    372400                // Sort by cache instance
    373                 qsort(pairings, cpus);
     401                qsort(pairings, cpus_c);
    374402
    375403                {
    376404                        unsigned it = 0;
    377                         for(i; cpus) {
     405                        RangeIter rc = { cpus };
     406                        while(moveNext(rc)) {
     407                                unsigned i = rc.com;
    378408                                unsigned llc_id = pairings[i].id;
    379409                                if(maps[llc_id].start == -1u) {
     
    384414                                }
    385415                        }
    386                         /* paranoid */ verify(it == cpus);
     416                        /* paranoid */ verify(it == cpus_c);
    387417                }
    388418
    389419                // From the mappings build the actual cpu map we want
    390                 struct cpu_map_entry_t * entries = alloc(cpus);
    391                 for(i; cpus) { entries[i].count = 0; }
    392                 for(i; cpus) {
     420                struct cpu_map_entry_t * entries = alloc(cpus_c);
     421                for(i; cpus_c) { entries[i].count = 0; }
     422
     423                RangeIter rc = { cpus };
     424                while(moveNext(rc)) {
     425                        unsigned i = rc.com;
    393426                        /* paranoid */ verify(pairings[i].id < map_cnt);
    394427                        unsigned c = pairings[i].cpu;
     
    406439                free(pairings);
    407440
    408                 for(i; cpus) {
    409                         for(j; cache_levels) {
     441                for(i; cpus_c) {
     442                        if( raw[i] ) for(j; cache_levels) {
    410443                                ^(raw[i][j]){};
    411444                        }
     
    415448
    416449                cpu_info.llc_map = entries;
    417                 cpu_info.hthrd_count = cpus;
     450                cpu_info.hthrd_count = cpus_c;
     451                cpu_info.llc_count = map_cnt;
    418452        }
    419453
Note: See TracChangeset for help on using the changeset viewer.