nested-structs/arrays (C)

Aberta
#8 0 comentários 0 reações 0 responsáveis Ver no GitHub

Ninguém assumiu esta issue ainda.

Avaliação

Dificuldade
4/5
Tempo estimado
3-5 dias
Facilidade para iniciantes
28/100
Tipo de issue
Funcionalidade
Clareza
Precisa de esclarecimento
Status de atividade
Estagnada
Stack de tecnologia
c, javascript
Domínio
tooling

Direção de pesquisa

Comece por tools/gen_lib.js, na região do loop de geração de structs, e revise os campos de structs de api.json, especialmente os tipos de arrays e structs aninhados que atualmente são ignorados. Verifique primeiro a issue #9 e, em seguida, inspecione os src/structs.h e src/lib.c gerados; considera-se concluído quando esses campos não forem mais omitidos silenciosamente dos utilitários gerados.

Escrita pelo modelo de indexação a partir do texto da issue.

Descrição

C enhancement todo

I am currently skipping these in C codegen. They should be addressed, once I figure out #9

https://github.com/konsumer/raylib-pointers/blob/f365325/tools/gen_lib.js#L22


// this will generate raylib-pointers

import { writeFile } from 'fs/promises'
import api from './api.json'

const { structs, wrapped } = api

let out = []

// build utils for structs
for (const { name, description, fields } of structs) {
  out.push(`// ${description}

unsigned int ${name}_size() {
  return sizeof(${name});
}`)
  for (const field of fields) {
    if (field.type.includes('[')) {
      // TODO: add utils for arrays
    } else if (/^[A-Z]/.test(field.type)) {
      // cheap way to detect raylib types
      // TODO: add utils for nested structs
    } else {
      out.push(`${field.type} ${name}_get_${field.name}(${name}* p) {\n  return p->${field.name};\n}`)
      out.push(`void ${name}_set_${field.name}(${name}* p, ${field.type} v) {\n  p->${field.name} = v;\n}`)
    }
  }
  out.push('')
}

await writeFile('src/structs.h', out.join('\n'))

out = [
  `#include <stdlib.h>
#include "raylib.h"

// utils for operating on structs
#include "./structs.h"

// this allows us to free anything that was allocated, last-frame
// max number of allocations you can do, per-frame
#define FRAME_ALLOC_SIZE 1024*512

int _frame_alloc_counter = 0;
void* _frame_allocated[FRAME_ALLOC_SIZE] = {};
bool running = false;

void* wrapped_alloc(size_t s) {
  void* p = RL_MALLOC(s);
  if (running) {
    _frame_allocated[_frame_alloc_counter] = p;
    _frame_alloc_counter = (_frame_alloc_counter + 1) % FRAME_ALLOC_SIZE;
  }
  return p;
}

void wrapped_free(void* p) {
  RL_FREE(p);
}

bool wrapped_WindowShouldClose() {
  running = true;
  for (int i=0;i<_frame_alloc_counter;i++) {
    wrapped_free(_frame_allocated[i]);
  }
  _frame_alloc_counter = 0;
  return WindowShouldClose();
}
`
]

// these will not be ghenerated for
const blocklist = [
  // I will be implementing my own mem-management stuff
  'wrapped_WindowShouldClose',
  'wrapped_free',
  'wrapped_alloc'
]

for (const { name, description, returnType, params, original } of wrapped) {
  if (blocklist.includes(name)) {
    continue
  }
  // does return need to be converted to a pointer?
  const returnPointer = /^[A-Z]/.test(returnType)

  // do any params need to be converted to pointers?
  let paramPointer = false

  const inputParams = params.map((p) => {
    if (/^[A-Z]/.test(p.type)) {
      paramPointer = true
      return `${p.type.trim()} ${p.name}`
    } else {
      return `${p.type} ${p.name}`
    }
  })

  const callParams = params.map((p) => {
    if (/^[A-Z]/.test(p.type)) {
      paramPointer = true
      return `*${p.name}`
    } else {
      return p.name
    }
  })

  out.push(`// ${description}`)
  if (returnPointer) {
    out.push(`${returnType} ${name}(${inputParams.join(', ')}) {`)
    out.push(`  ${returnType} _ret = wrapped_alloc(sizeof(${returnType.replace('*', '')}));`)
    out.push(`  *_ret = ${original}(${callParams.join(', ')});`)
    out.push('  return _ret;')
  } else {
    out.push(`${returnType} ${name}(${inputParams.join(', ')}) {`)
    if (returnType === 'void') {
      out.push(`  ${original}(${callParams.join(', ')});`)
    } else {
      out.push(`  return ${original}(${callParams.join(', ')});`)
    }
  }
  out.push('}\n')
}

await writeFile('src/lib.c', out.join('\n'))

Linguagem predominante
C
Estrelas
0
Forks
1
Métricas de merge de PRs
Nenhum PR com merge em 30d

Preparar o ambiente

Este projeto não oferece contêiner de desenvolvimento, Dockerfile nem guia de contribuição, então a configuração fica por sua conta: comece pelo README e veja nosso guia da primeira contribuição para os passos gerais.

Primeiros passos

  1. Leia a issue inteira e depois o guia de contribuição do projeto.
  2. Comente na issue dizendo que vai assumir — evita que duas pessoas façam o mesmo trabalho.
  3. Faça um fork do repositório e trabalhe em uma branch.
  4. Abra um pull request que referencie o número da issue.

Mais de konsumer/raylib-pointers

Todas as issues de konsumer/raylib-pointers

Issues semelhantes

Mais issues de C

Receba novas issues na sua caixa de entrada

Um resumo curto de issues do GitHub para quem está começando.