kit

kit
git clone https://git.ryansepassi.com/git/kit.git
Log | Files | Refs | README

local.c (4656B)


      1 #include "cg/internal.h"
      2 
      3 int api_local_requires_memory(KitCg* g, KitCgTypeId ty, KitCgLocalAttrs attrs) {
      4   u32 hidden_flags = KIT_CG_LOCAL_ARTIFICIAL | KIT_CG_LOCAL_OPTIMIZED_OUT |
      5                      KIT_CG_LOCAL_COMPILER_TEMP;
      6   if (attrs.flags & KIT_CG_LOCAL_MEMORY_REQUIRED) return 1;
      7   if (g && g->debug && attrs.name && (attrs.flags & hidden_flags) == 0)
      8     return 1;
      9   /* Aggregates (records, arrays), wide16 (f128/i128), split-lane wide8, vararg
     10    * state, and any non-scalar type must live in memory. */
     11   if (api_is_wide16_scalar_type(g->c, ty)) return 1;
     12   if (api_is_wide8_scalar_type(g->c, ty)) return 1;
     13   /* int||float||ptr, in one type decode instead of three. */
     14   return !(api_type_pred_bits(g->c, ty) &
     15            (API_PRED_INT | API_PRED_FLOAT | API_PRED_PTR));
     16 }
     17 
     18 KitCgLocal api_local_handle(u32 index) {
     19   u32 raw = index + 1u;
     20   if (!raw) return KIT_CG_LOCAL_NONE;
     21   return raw;
     22 }
     23 
     24 int api_grow_locals(KitCg* g, u32 want) {
     25   Heap* h = g->c->ctx->heap;
     26   ApiSourceLocal* nb;
     27   u32 cap;
     28   if (g->locals_cap >= want) return 1;
     29   cap = g->locals_cap ? g->locals_cap : 16u;
     30   while (cap < want) cap *= 2u;
     31   nb =
     32       (ApiSourceLocal*)h->alloc(h, sizeof(*nb) * cap, _Alignof(ApiSourceLocal));
     33   if (!nb) return 0;
     34   memset(nb, 0, sizeof(*nb) * cap);
     35   if (g->locals) {
     36     memcpy(nb, g->locals, sizeof(*nb) * g->nlocals);
     37     h->free(h, g->locals, sizeof(*g->locals) * g->locals_cap);
     38   }
     39   g->locals = nb;
     40   g->locals_cap = cap;
     41   return 1;
     42 }
     43 
     44 ApiSourceLocal* api_local_from_handle(KitCg* g, KitCgLocal local) {
     45   u32 index;
     46   if (local == KIT_CG_LOCAL_NONE) return NULL;
     47   index = local - 1u;
     48   if (index >= g->nlocals) {
     49     return NULL;
     50   }
     51   return &g->locals[index];
     52 }
     53 
     54 CGLocal api_frame_local_storage(KitCg* g, const CGLocalDesc* d) {
     55   return g->target->local(g->target, d);
     56 }
     57 
     58 KitCgLocal kit_cg_local(KitCg* g, KitCgTypeId type, KitCgLocalAttrs attrs) {
     59   KitCgTypeId ty;
     60   CGLocalDesc desc;
     61   CGLocal storage;
     62   ApiSourceLocal* rec;
     63   KitCgLocal handle;
     64   if (!g) return KIT_CG_LOCAL_NONE;
     65   ty = resolve_type(g->c, type);
     66   if (!ty) return KIT_CG_LOCAL_NONE;
     67   handle = api_local_handle(g->nlocals);
     68   if (handle == KIT_CG_LOCAL_NONE || !api_grow_locals(g, g->nlocals + 1u))
     69     return KIT_CG_LOCAL_NONE;
     70   memset(&desc, 0, sizeof desc);
     71   desc.type = ty;
     72   desc.name = (Sym)attrs.name;
     73   desc.loc = g->cur_loc;
     74   desc.size = abi_cg_sizeof(g->c->abi, ty);
     75   desc.align = attrs.align ? attrs.align : abi_cg_alignof(g->c->abi, ty);
     76   if (api_local_requires_memory(g, ty, attrs))
     77     desc.flags |= CG_LOCAL_MEMORY_REQUIRED;
     78   if (api_unevaluated(g)) {
     79     storage = CG_LOCAL_NONE;
     80   } else if (g->target->local)
     81     storage = g->target->local(g->target, &desc);
     82   else
     83     storage = api_frame_local_storage(g, &desc);
     84   rec = &g->locals[g->nlocals++];
     85   memset(rec, 0, sizeof *rec);
     86   rec->type = ty;
     87   rec->name = attrs.name;
     88   rec->attrs = attrs;
     89   rec->loc = g->cur_loc;
     90   rec->desc = desc;
     91   rec->storage = storage;
     92   rec->param_index = 0;
     93   rec->kind = API_SOURCE_LOCAL_AUTO;
     94   return handle;
     95 }
     96 
     97 KitCgLocal kit_cg_param(KitCg* g, uint32_t index, KitCgTypeId type,
     98                         KitCgLocalAttrs attrs) {
     99   KitCgTypeId ty;
    100   CGParamDesc pd;
    101   ApiSourceLocal* rec;
    102   KitCgLocal handle;
    103   CGLocal storage;
    104   u32 size;
    105   u32 align;
    106   if (!g) return KIT_CG_LOCAL_NONE;
    107   ty = resolve_type(g->c, type);
    108   if (!ty) return KIT_CG_LOCAL_NONE;
    109   if (index != g->nlocals) return KIT_CG_LOCAL_NONE;
    110   handle = api_local_handle(g->nlocals);
    111   if (handle == KIT_CG_LOCAL_NONE || !api_grow_locals(g, g->nlocals + 1u))
    112     return KIT_CG_LOCAL_NONE;
    113 
    114   size = abi_cg_sizeof(g->c->abi, ty);
    115   align = attrs.align ? attrs.align : abi_cg_alignof(g->c->abi, ty);
    116 
    117   memset(&pd, 0, sizeof pd);
    118   pd.index = index;
    119   pd.name = (Sym)attrs.name;
    120   pd.type = ty;
    121   pd.size = size;
    122   pd.align = align;
    123   if (api_local_requires_memory(g, ty, attrs))
    124     pd.flags |= CG_LOCAL_MEMORY_REQUIRED;
    125   pd.loc = g->cur_loc;
    126   storage =
    127       api_unevaluated(g) ? CG_LOCAL_NONE : g->target->param(g->target, &pd);
    128 
    129   rec = &g->locals[g->nlocals++];
    130   memset(rec, 0, sizeof *rec);
    131   rec->type = ty;
    132   rec->name = attrs.name;
    133   rec->attrs = attrs;
    134   rec->loc = g->cur_loc;
    135   memset(&rec->desc, 0, sizeof rec->desc);
    136   rec->desc.type = ty;
    137   rec->desc.name = (Sym)attrs.name;
    138   rec->desc.loc = g->cur_loc;
    139   rec->desc.size = size;
    140   rec->desc.align = align;
    141   rec->desc.flags = pd.flags;
    142   rec->storage = storage;
    143   rec->param_index = index;
    144   rec->kind = API_SOURCE_LOCAL_PARAM;
    145   return handle;
    146 }
    147 
    148 /* ============================================================
    149  * Push operations
    150  * ============================================================ */