mirror of
https://git.code.sf.net/p/quake/quakeforge
synced 2024-11-22 20:41:20 +00:00
[vkgen] Add support for labeled array elements
This treats dictionary items as arrays ordered by key creation (ie, the order of the key/value pairs in the dictionary is preserved). The label is written to the specified field when parsing the struct. Both actual arrays and single element "arrays" are supported.
This commit is contained in:
parent
061f90ab83
commit
3498d8b2ae
9 changed files with 200 additions and 4 deletions
|
@ -12,6 +12,8 @@ vkgen_dat_src= \
|
||||||
libs/video/renderer/vulkan/vkgen/vkfielddata.r \
|
libs/video/renderer/vulkan/vkgen/vkfielddata.r \
|
||||||
libs/video/renderer/vulkan/vkgen/vkfielddef.r \
|
libs/video/renderer/vulkan/vkgen/vkfielddef.r \
|
||||||
libs/video/renderer/vulkan/vkgen/vkfieldignore.r \
|
libs/video/renderer/vulkan/vkgen/vkfieldignore.r \
|
||||||
|
libs/video/renderer/vulkan/vkgen/vkfieldlabeledarray.r \
|
||||||
|
libs/video/renderer/vulkan/vkgen/vkfieldlabeledsingle.r \
|
||||||
libs/video/renderer/vulkan/vkgen/vkfieldreadonly.r \
|
libs/video/renderer/vulkan/vkgen/vkfieldreadonly.r \
|
||||||
libs/video/renderer/vulkan/vkgen/vkfieldsingle.r \
|
libs/video/renderer/vulkan/vkgen/vkfieldsingle.r \
|
||||||
libs/video/renderer/vulkan/vkgen/vkfieldstring.r \
|
libs/video/renderer/vulkan/vkgen/vkfieldstring.r \
|
||||||
|
@ -57,6 +59,8 @@ EXTRA_DIST += \
|
||||||
libs/video/renderer/vulkan/vkgen/vkfielddata.h \
|
libs/video/renderer/vulkan/vkgen/vkfielddata.h \
|
||||||
libs/video/renderer/vulkan/vkgen/vkfielddef.h \
|
libs/video/renderer/vulkan/vkgen/vkfielddef.h \
|
||||||
libs/video/renderer/vulkan/vkgen/vkfieldignore.h \
|
libs/video/renderer/vulkan/vkgen/vkfieldignore.h \
|
||||||
|
libs/video/renderer/vulkan/vkgen/vkfieldlabeledarray.h \
|
||||||
|
libs/video/renderer/vulkan/vkgen/vkfieldlabeledsingle.h \
|
||||||
libs/video/renderer/vulkan/vkgen/vkfieldreadonly.h \
|
libs/video/renderer/vulkan/vkgen/vkfieldreadonly.h \
|
||||||
libs/video/renderer/vulkan/vkgen/vkfieldsingle.h \
|
libs/video/renderer/vulkan/vkgen/vkfieldsingle.h \
|
||||||
libs/video/renderer/vulkan/vkgen/vkfieldstring.h \
|
libs/video/renderer/vulkan/vkgen/vkfieldstring.h \
|
||||||
|
|
|
@ -7,6 +7,8 @@
|
||||||
#include "vkfielddata.h"
|
#include "vkfielddata.h"
|
||||||
#include "vkfielddef.h"
|
#include "vkfielddef.h"
|
||||||
#include "vkfieldignore.h"
|
#include "vkfieldignore.h"
|
||||||
|
#include "vkfieldlabeledarray.h"
|
||||||
|
#include "vkfieldlabeledsingle.h"
|
||||||
#include "vkfieldreadonly.h"
|
#include "vkfieldreadonly.h"
|
||||||
#include "vkfieldsingle.h"
|
#include "vkfieldsingle.h"
|
||||||
#include "vkfieldstring.h"
|
#include "vkfieldstring.h"
|
||||||
|
@ -44,6 +46,10 @@
|
||||||
return [[[SingleField alloc] init:item struct:strct field:fname] autorelease];
|
return [[[SingleField alloc] init:item struct:strct field:fname] autorelease];
|
||||||
case "array":
|
case "array":
|
||||||
return [[[ArrayField alloc] init:item struct:strct field:fname] autorelease];
|
return [[[ArrayField alloc] init:item struct:strct field:fname] autorelease];
|
||||||
|
case "labeledarray":
|
||||||
|
return [[[LabeledArrayField alloc] init:item struct:strct field:fname] autorelease];
|
||||||
|
case "labeledsingle":
|
||||||
|
return [[[LabeledSingleField alloc] init:item struct:strct field:fname] autorelease];
|
||||||
case "readonly":
|
case "readonly":
|
||||||
return [[[ReadOnlyField alloc] init:item struct:strct field:fname] autorelease];
|
return [[[ReadOnlyField alloc] init:item struct:strct field:fname] autorelease];
|
||||||
case "ignore":
|
case "ignore":
|
||||||
|
|
11
libs/video/renderer/vulkan/vkgen/vkfieldlabeledarray.h
Normal file
11
libs/video/renderer/vulkan/vkgen/vkfieldlabeledarray.h
Normal file
|
@ -0,0 +1,11 @@
|
||||||
|
#ifndef __renderer_vulkan_vkgen_vkfieldlabeledarray_h
|
||||||
|
#define __renderer_vulkan_vkgen_vkfieldlabeledarray_h
|
||||||
|
|
||||||
|
#include "vkfieldarray.h"
|
||||||
|
|
||||||
|
@interface LabeledArrayField: ArrayField
|
||||||
|
{
|
||||||
|
}
|
||||||
|
@end
|
||||||
|
|
||||||
|
#endif//__renderer_vulkan_vkgen_vkfieldlabeledarray_h
|
37
libs/video/renderer/vulkan/vkgen/vkfieldlabeledarray.r
Normal file
37
libs/video/renderer/vulkan/vkgen/vkfieldlabeledarray.r
Normal file
|
@ -0,0 +1,37 @@
|
||||||
|
#include <PropertyList.h>
|
||||||
|
|
||||||
|
#include "vkfieldlabeledarray.h"
|
||||||
|
#include "vkfieldtype.h"
|
||||||
|
#include "vkgen.h"
|
||||||
|
#include "vkstruct.h"
|
||||||
|
#include "vktype.h"
|
||||||
|
|
||||||
|
@implementation LabeledArrayField
|
||||||
|
|
||||||
|
-init:(PLItem *) item struct:(Struct *)strct field:(string)fname
|
||||||
|
{
|
||||||
|
self = [super init:item struct:strct field:fname];
|
||||||
|
if (!self) {
|
||||||
|
return self;
|
||||||
|
}
|
||||||
|
|
||||||
|
PLItem *desc = [item getObjectForKey:"type"];
|
||||||
|
string label_field = [[desc getObjectAtIndex:2] string];
|
||||||
|
Type *t = [[Type lookup:[type type]] resolveType];
|
||||||
|
if ([t isKindOfClass:[Struct class]]) {
|
||||||
|
Struct *s = (Struct *) t;
|
||||||
|
[s setLabelField:label_field];
|
||||||
|
}
|
||||||
|
|
||||||
|
return self;
|
||||||
|
}
|
||||||
|
|
||||||
|
-writeField
|
||||||
|
{
|
||||||
|
fprintf (output_file, "\t{\"%s\", 0, %s, parse_%s, &parse_%s_%s_data},\n",
|
||||||
|
field_name, "QFDictionary", "labeledarray", struct_name,
|
||||||
|
field_name);
|
||||||
|
return self;
|
||||||
|
}
|
||||||
|
|
||||||
|
@end
|
11
libs/video/renderer/vulkan/vkgen/vkfieldlabeledsingle.h
Normal file
11
libs/video/renderer/vulkan/vkgen/vkfieldlabeledsingle.h
Normal file
|
@ -0,0 +1,11 @@
|
||||||
|
#ifndef __renderer_vulkan_vkgen_vkfieldlabeledsingle_h
|
||||||
|
#define __renderer_vulkan_vkgen_vkfieldlabeledsingle_h
|
||||||
|
|
||||||
|
#include "vkfieldsingle.h"
|
||||||
|
|
||||||
|
@interface LabeledSingleField: SingleField
|
||||||
|
{
|
||||||
|
}
|
||||||
|
@end
|
||||||
|
|
||||||
|
#endif//__renderer_vulkan_vkgen_vkfieldlabeledsingle_h
|
37
libs/video/renderer/vulkan/vkgen/vkfieldlabeledsingle.r
Normal file
37
libs/video/renderer/vulkan/vkgen/vkfieldlabeledsingle.r
Normal file
|
@ -0,0 +1,37 @@
|
||||||
|
#include <PropertyList.h>
|
||||||
|
|
||||||
|
#include "vkfieldlabeledsingle.h"
|
||||||
|
#include "vkfieldtype.h"
|
||||||
|
#include "vkgen.h"
|
||||||
|
#include "vkstruct.h"
|
||||||
|
#include "vktype.h"
|
||||||
|
|
||||||
|
@implementation LabeledSingleField
|
||||||
|
|
||||||
|
-init:(PLItem *) item struct:(Struct *)strct field:(string)fname
|
||||||
|
{
|
||||||
|
self = [super init:item struct:strct field:fname];
|
||||||
|
if (!self) {
|
||||||
|
return self;
|
||||||
|
}
|
||||||
|
|
||||||
|
PLItem *desc = [item getObjectForKey:"type"];
|
||||||
|
string label_field = [[desc getObjectAtIndex:2] string];
|
||||||
|
Type *t = [[Type lookup:[type type]] resolveType];
|
||||||
|
if ([t isKindOfClass:[Struct class]]) {
|
||||||
|
Struct *s = (Struct *) t;
|
||||||
|
[s setLabelField:label_field];
|
||||||
|
}
|
||||||
|
|
||||||
|
return self;
|
||||||
|
}
|
||||||
|
|
||||||
|
-writeField
|
||||||
|
{
|
||||||
|
fprintf (output_file, "\t{\"%s\", 0, %s, parse_%s, &parse_%s_%s_data},\n",
|
||||||
|
field_name, "QFDictionary", "labeledsingle", struct_name,
|
||||||
|
field_name);
|
||||||
|
return self;
|
||||||
|
}
|
||||||
|
|
||||||
|
@end
|
|
@ -11,10 +11,12 @@
|
||||||
@interface Struct: Type
|
@interface Struct: Type
|
||||||
{
|
{
|
||||||
string outname;
|
string outname;
|
||||||
|
string label_field;
|
||||||
int write_symtab;
|
int write_symtab;
|
||||||
}
|
}
|
||||||
-(void) queueFieldTypes;
|
-(void) queueFieldTypes;
|
||||||
-(qfot_var_t *)findField:(string) fieldName;
|
-(qfot_var_t *)findField:(string) fieldName;
|
||||||
|
-(void) setLabelField:(string) label_field;
|
||||||
-(void) writeForward;
|
-(void) writeForward;
|
||||||
-(void) writeTable;
|
-(void) writeTable;
|
||||||
-(void) writeSymtabInit;
|
-(void) writeSymtabInit;
|
||||||
|
|
|
@ -12,6 +12,12 @@
|
||||||
|
|
||||||
@implementation Struct
|
@implementation Struct
|
||||||
|
|
||||||
|
-(void) dealloc
|
||||||
|
{
|
||||||
|
str_free (outname);
|
||||||
|
str_free (label_field);
|
||||||
|
}
|
||||||
|
|
||||||
-(string) name
|
-(string) name
|
||||||
{
|
{
|
||||||
return str_mid(type.strct.tag, 4);
|
return str_mid(type.strct.tag, 4);
|
||||||
|
@ -67,7 +73,7 @@
|
||||||
-(string)sTypeName
|
-(string)sTypeName
|
||||||
{
|
{
|
||||||
string s = "VK_STRUCTURE_TYPE";
|
string s = "VK_STRUCTURE_TYPE";
|
||||||
string name = str_hold ([self outname]);
|
string name = [self outname];
|
||||||
int length = strlen (name);
|
int length = strlen (name);
|
||||||
int start, end, c;
|
int start, end, c;
|
||||||
for (start = 2; start < length; start = end) {
|
for (start = 2; start < length; start = end) {
|
||||||
|
@ -83,6 +89,11 @@
|
||||||
return str_upper (s);
|
return str_upper (s);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
-(void) setLabelField:(string)label_field
|
||||||
|
{
|
||||||
|
self.label_field = label_field;
|
||||||
|
}
|
||||||
|
|
||||||
-(void) writeForward
|
-(void) writeForward
|
||||||
{
|
{
|
||||||
PLItem *field_dict = [parse getObjectForKey:[self name]];
|
PLItem *field_dict = [parse getObjectForKey:[self name]];
|
||||||
|
@ -183,6 +194,11 @@
|
||||||
fprintf (output_file, "\t((%s *) data)->sType", [self outname]);
|
fprintf (output_file, "\t((%s *) data)->sType", [self outname]);
|
||||||
fprintf (output_file, " = %s;\n", [self sTypeName]);
|
fprintf (output_file, " = %s;\n", [self sTypeName]);
|
||||||
}
|
}
|
||||||
|
if (label_field) {
|
||||||
|
fprintf (output_file, "\t((%s *) data)->%s", [self outname],
|
||||||
|
label_field);
|
||||||
|
fprintf (output_file, " = vkstrdup (context, field->name);\n");
|
||||||
|
}
|
||||||
fprintf (output_file,
|
fprintf (output_file,
|
||||||
"\tif (PL_Type (item) == QFString\n"
|
"\tif (PL_Type (item) == QFString\n"
|
||||||
"\t\t&& !(item = parse_reference (item, \"%s\", messages, context))) {\n"
|
"\t\t&& !(item = parse_reference (item, \"%s\", messages, context))) {\n"
|
||||||
|
|
|
@ -303,6 +303,34 @@ parse_ignore (const plfield_t *field, const plitem_t *item,
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int __attribute__((used))
|
||||||
|
parse_labeledsingle (const plfield_t *field, const plitem_t *item,
|
||||||
|
void *data, plitem_t *messages, void *context)
|
||||||
|
{
|
||||||
|
__auto_type single = (parse_single_t *) field->data;
|
||||||
|
void *flddata = (byte *)data + single->value_offset;
|
||||||
|
|
||||||
|
//Sys_MaskPrintf (SYS_vulkan_parse,"parse_labeledsingle: %s %zd %d %p %p\n",
|
||||||
|
// field->name, field->offset,
|
||||||
|
// field->type, field->parser, field->data);
|
||||||
|
|
||||||
|
if (!PL_CheckType (single->type, PL_Type (item))) {
|
||||||
|
PL_TypeMismatch (messages, item, field->name, single->type,
|
||||||
|
PL_Type (item));
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
plfield_t f = { 0, 0, single->type, single->parser, 0 };
|
||||||
|
void *value = vkparse_alloc (context, single->stride);
|
||||||
|
memset (value, 0, single->stride);
|
||||||
|
if (!single->parser (&f, item, value, messages, context)) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
*(void **) flddata = value;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
static int
|
static int
|
||||||
parse_single (const plfield_t *field, const plitem_t *item,
|
parse_single (const plfield_t *field, const plitem_t *item,
|
||||||
void *data, plitem_t *messages, void *context)
|
void *data, plitem_t *messages, void *context)
|
||||||
|
@ -331,6 +359,43 @@ parse_single (const plfield_t *field, const plitem_t *item,
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int __attribute__((used))
|
||||||
|
parse_labeledarray (const plfield_t *field, const plitem_t *item,
|
||||||
|
void *data, plitem_t *messages, void *context)
|
||||||
|
{
|
||||||
|
__auto_type array = (parse_array_t *) field->data;
|
||||||
|
__auto_type value = (void **) ((byte *)data + array->value_offset);
|
||||||
|
__auto_type size = (uint32_t *) ((byte *)data + array->size_offset);
|
||||||
|
|
||||||
|
plelement_t element = {
|
||||||
|
array->type,
|
||||||
|
array->stride,
|
||||||
|
vkparse_alloc,
|
||||||
|
array->parser,
|
||||||
|
array->data,
|
||||||
|
};
|
||||||
|
plfield_t f = { 0, 0, 0, 0, &element };
|
||||||
|
|
||||||
|
typedef struct arr_s DARRAY_TYPE(byte) arr_t;
|
||||||
|
arr_t *arr;
|
||||||
|
|
||||||
|
//Sys_MaskPrintf (SYS_vulkan_parse, "parse_array: %s %zd %d %p %p %p\n",
|
||||||
|
// field->name, field->offset, field->type, field->parser,
|
||||||
|
// field->data, data);
|
||||||
|
//Sys_MaskPrintf (SYS_vulkan_parse, " %d %zd %p %zd %zd\n", array->type,
|
||||||
|
// array->stride, array->parser, array->value_offset,
|
||||||
|
// array->size_offset);
|
||||||
|
if (!PL_ParseLabeledArray (&f, item, &arr, messages, context)) {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
*value = vkparse_alloc (context, array->stride * arr->size);
|
||||||
|
memcpy (*value, arr->a, array->stride * arr->size);
|
||||||
|
if ((void *) size >= data) {
|
||||||
|
*size = arr->size;
|
||||||
|
}
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
static int
|
static int
|
||||||
parse_array (const plfield_t *field, const plitem_t *item,
|
parse_array (const plfield_t *field, const plitem_t *item,
|
||||||
void *data, plitem_t *messages, void *context)
|
void *data, plitem_t *messages, void *context)
|
||||||
|
@ -395,6 +460,15 @@ parse_fixed_array (const plfield_t *field, const plitem_t *item,
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static char *
|
||||||
|
vkstrdup (parsectx_t *context, const char *str)
|
||||||
|
{
|
||||||
|
size_t len = strlen (str) + 1;
|
||||||
|
char *dup = vkparse_alloc (context, len);
|
||||||
|
memcpy (dup, str, len);
|
||||||
|
return dup;
|
||||||
|
}
|
||||||
|
|
||||||
static int
|
static int
|
||||||
parse_string (const plfield_t *field, const plitem_t *item,
|
parse_string (const plfield_t *field, const plitem_t *item,
|
||||||
void *data, plitem_t *messages, void *context)
|
void *data, plitem_t *messages, void *context)
|
||||||
|
@ -410,9 +484,7 @@ parse_string (const plfield_t *field, const plitem_t *item,
|
||||||
//Sys_MaskPrintf (SYS_vulkan_parse, " %zd\n", string->value_offset);
|
//Sys_MaskPrintf (SYS_vulkan_parse, " %zd\n", string->value_offset);
|
||||||
//Sys_MaskPrintf (SYS_vulkan_parse, " %s\n", str);
|
//Sys_MaskPrintf (SYS_vulkan_parse, " %s\n", str);
|
||||||
|
|
||||||
size_t len = strlen (str) + 1;
|
*value = vkstrdup (context, str);
|
||||||
*value = vkparse_alloc (context, len);
|
|
||||||
memcpy (*value, str, len);
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue