gskspvwriter: Allow writing a function with initializer

That way, we can initialize global variables.

We're also a lot closer to emitting code in the way glslc does.
This commit is contained in:
Benjamin Otte
2017-10-07 21:13:18 +02:00
parent 1455ef2c21
commit 17661af6da
6 changed files with 63 additions and 16 deletions

View File

@@ -56,7 +56,9 @@ struct _GskSlFunctionClass {
void (* print) (const GskSlFunction *function,
GskSlPrinter *printer);
guint32 (* write_spv) (const GskSlFunction *function,
GskSpvWriter *writer);
GskSpvWriter *writer,
GskSpvWriterFunc initializer,
gpointer initializer_data);
guint32 (* write_call_spv) (GskSlFunction *function,
GskSpvWriter *writer,
guint32 *arguments);
@@ -146,8 +148,12 @@ gsk_sl_function_constructor_print (const GskSlFunction *function,
static guint32
gsk_sl_function_constructor_write_spv (const GskSlFunction *function,
GskSpvWriter *writer)
GskSpvWriter *writer,
GskSpvWriterFunc initializer,
gpointer initializer_data)
{
g_assert (initializer == NULL);
return 0;
}
@@ -240,8 +246,12 @@ gsk_sl_function_native_print (const GskSlFunction *function,
static guint32
gsk_sl_function_native_write_spv (const GskSlFunction *function,
GskSpvWriter *writer)
GskSpvWriter *writer,
GskSpvWriterFunc initializer,
gpointer initializer_data)
{
g_assert (initializer != NULL);
return 0;
}
@@ -378,7 +388,9 @@ gsk_sl_function_declared_print (const GskSlFunction *function,
static guint32
gsk_sl_function_declared_write_spv (const GskSlFunction *function,
GskSpvWriter *writer)
GskSpvWriter *writer,
GskSpvWriterFunc initializer,
gpointer initializer_data)
{
GskSlFunctionDeclared *declared = (GskSlFunctionDeclared *) function;
guint32 return_type_id, function_type_id, function_id;
@@ -407,7 +419,8 @@ gsk_sl_function_declared_write_spv (const GskSlFunction *function,
}
/* add function body */
gsk_spv_writer_label (writer);
if (initializer)
initializer (writer, initializer_data);
gsk_sl_statement_write_spv (declared->statement, writer);
@@ -659,9 +672,11 @@ gsk_sl_function_print (const GskSlFunction *function,
guint32
gsk_sl_function_write_spv (const GskSlFunction *function,
GskSpvWriter *writer)
GskSpvWriter *writer,
GskSpvWriterFunc initializer,
gpointer initializer_data)
{
return function->class->write_spv (function, writer);
return function->class->write_spv (function, writer, initializer, initializer_data);
}
guint32

View File

@@ -47,7 +47,9 @@ GskSlValue * gsk_sl_function_get_constant (const GskSlFunc
GskSlValue **values,
gsize n_values);
guint32 gsk_sl_function_write_spv (const GskSlFunction *function,
GskSpvWriter *writer);
GskSpvWriter *writer,
GskSpvWriterFunc initializer,
gpointer initializer_data);
guint32 gsk_sl_function_write_call_spv (GskSlFunction *function,
GskSpvWriter *writer,
guint32 *arguments);

View File

@@ -255,21 +255,33 @@ gsk_sl_program_print (GskSlProgram *program,
gsk_sl_printer_unref (printer);
}
static void
gsk_sl_program_write_spv_initializer (GskSpvWriter *writer,
gpointer data)
{
GskSlProgram *program = data;
GSList *l;
for (l = program->variables; l; l = l->next)
gsk_spv_writer_get_id_for_variable (writer, l->data);
}
static void
gsk_sl_program_write_spv (GskSlProgram *program,
GskSpvWriter *writer)
{
GSList *l;
for (l = program->variables; l; l = l->next)
gsk_spv_writer_get_id_for_variable (writer, l->data);
for (l = program->functions; l; l = l->next)
{
gsk_spv_writer_get_id_for_function (writer, l->data);
if (g_str_equal (gsk_sl_function_get_name (l->data), "main"))
gsk_spv_writer_set_entry_point (writer, l->data);
{
gsk_spv_writer_write_function (writer,
l->data,
gsk_sl_program_write_spv_initializer,
program);
gsk_spv_writer_set_entry_point (writer, l->data);
}
}
}

View File

@@ -37,6 +37,7 @@ typedef struct _GskSlValue GskSlValue;
typedef struct _GskSlVariable GskSlVariable;
typedef struct _GskSpvWriter GskSpvWriter;
typedef void (* GskSpvWriterFunc) (GskSpvWriter *, gpointer);
typedef enum {
GSK_SL_VOID,

View File

@@ -325,15 +325,28 @@ guint32
gsk_spv_writer_get_id_for_function (GskSpvWriter *writer,
GskSlFunction *function)
{
GskSpvCodeBlock *block;
guint32 result;
result = GPOINTER_TO_UINT (g_hash_table_lookup (writer->functions, function));
if (result != 0)
return result;
return gsk_spv_writer_write_function (writer, function, NULL, NULL);
}
guint32
gsk_spv_writer_write_function (GskSpvWriter *writer,
GskSlFunction *function,
GskSpvWriterFunc initializer,
gpointer initializer_data)
{
GskSpvCodeBlock *block;
guint32 result;
g_assert (g_hash_table_lookup (writer->functions, function) == NULL);
gsk_spv_writer_push_new_code_block (writer);
result = gsk_sl_function_write_spv (function, writer);
result = gsk_sl_function_write_spv (function, writer, initializer, initializer_data);
g_hash_table_insert (writer->functions, gsk_sl_function_ref (function), GUINT_TO_POINTER (result));
block = gsk_spv_writer_pop_code_block (writer);
writer->pending_blocks = g_slist_prepend (writer->pending_blocks, block);

View File

@@ -71,6 +71,10 @@ guint32 gsk_spv_writer_get_id_for_variable (GskSpvWriter
GskSlVariable *variable);
guint32 gsk_spv_writer_get_id_for_function (GskSpvWriter *writer,
GskSlFunction *function);
guint32 gsk_spv_writer_write_function (GskSpvWriter *writer,
GskSlFunction *function,
GskSpvWriterFunc initializer,
gpointer intializer_data);
guint32 gsk_spv_writer_make_id (GskSpvWriter *writer);
GArray * gsk_spv_writer_get_bytes (GskSpvWriter *writer,