Skip to content

Instantly share code, notes, and snippets.

@Xliff
Last active April 18, 2016 15:04
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Xliff/b079adbbb9e4661d308119a4f5681cb8 to your computer and use it in GitHub Desktop.
Save Xliff/b079adbbb9e4661d308119a4f5681cb8 to your computer and use it in GitHub Desktop.

Updated! See below...

Code excerpt:

class TreeStruct is repr('CStruct') {
  # ref
  has Pointer #`{myhtml_t*}                    $.myhtml;
  has Pointer #`{mchar_async_t*}               $.mchar;
  has Pointer #`{myhtml_token_t*}              $.token;
  has Pointer #`{mcobject_async_t*}            $.tree_obj;
  has Pointer #`{mcsync_t*}                    $.sync;
  has Pointer #`{mythread_queue_list_entry_t*} $.queue_entry;
  has Pointer #`{mythread_queue_t*}            $.queue;
  has Pointer #`{myhtml_tag_t*}                $.tags;

  # init id's
  has uint32                              $.mcasync_token_id;
  has uint32                              $.mcasync_attr_id;
  has uint32                              $.mcasync_tree_id;
  has uint32                              $.mchar_node_id;
  has uint32                              $.mcasync_incoming_buf_id;
  has Pointer #`{myhtml_token_attr_t*}    $.attr_current;
  has uint32 #`{myhtml_tag_id_t}          $.tmp_tag_id;
  has Pointer #`{mythread_queue_node_t*}  $.current_qnode;
  has Pointer #`{myhtml_incoming_buf_t*}  $.incoming_buf;
  has Pointer #`{myhtml_incoming_buf_t*}  $.incoming_buf_first;

  has Pointer #`{myhtml_tree_indexes_t*}  $.indexes;

  # ref for nodes
  has Pointer #`{myhtml_tree_node_t*}     $.document;
  has Pointer #`{myhtml_tree_node_t*}     $.fragment;
  has Pointer #`{myhtml_tree_node_t*}     $.node_head;
  has Pointer #`{myhtml_tree_node_t*}     $.node_html;
  has Pointer #`{myhtml_tree_node_t*}     $.node_body;
  has Pointer #`{myhtml_tree_node_t*}     $.node_form;
  has TreeDocType                         $.doctype;

  # for build tree
  has Pointer #`{myhtml_tree_list_t*}           $.active_formatting;
  has Pointer #`{myhtml_tree_list_t*}           $.open_elements;
  has Pointer #`{myhtml_tree_list_t*}           $.other_elements;
  has Pointer #`{myhtml_tree_token_list_t*}     $.token_list;
  has Pointer #`{myhtml_tree_insertion_list_t*} $.template_insertion;
  has Pointer #`{myhtml_async_args_t*}          $.async_args;
  has Pointer #`{myhtml_tree_temp_stream_t*}    $.temp_stream;
  has Pointer #`{myhtml_token_node_t* volatile} $.token_last_done is rw;

  # for detect namespace out of tree builder
  has Pointer #`{myhtml_token_node_t*}          $.token_namespace;

  # tree params
  has int32 #`{enum myhtml_tokenizer_state}     $.state;
  has int32 #`{enum myhtml_tokenizer_state}     $.state_of_builder;
  has int32 #`{enum myhtml_insertion_mode}      $.insert_mode;
  has int32 #`{enum myhtml_insertion_mode}      $.orig_insert_mode;
  has int32 #`{enum myhtml_tree_compat_mode}    $.compat_mode;
  has int32 #`{volatile enum myhtml_tree_flags} $.flags is rw;
  has bool                                      $.foster_parenting;
  has uint32                                    $.global_offset;

  has int32 #`{myhtml_encoding_t}            $.encoding;
  has int32 #`{myhtml_encoding_t}            $.encoding_usereq;
  has int32 #`{myhtml_tree_temp_tag_name_t}  $.temp_tag_name;

}

class Native_MyHTML is repr('CStruct') is export {
  has Pointer           $.thread;
  has Pointer           $.async_incoming_buf;
  has Pointer           $.mchar;
  has Pointer           $.tag_index;
  has Pointer           $.parse_state_func;
  has Pointer           $.insertion_func;

  # cw: uint32 to stand in for enum myhtml_options, for now.
  has uint32            $.opt;
  has Pointer           $.marker;
}

sub myhtml_tree_init(
  Pointer[TreeStruct],
  Pointer[Native_MyHTML]
) is native(&lib) returns int32 {*}

method new($myhtml) {
  my $mytree = myhtml_tree_create();
  say "tree created {$mytree}";
  my Native_MyHTML $myhtml2 .= new();
  say "myhtml2 created {$myhtml2}";
  say myhtml_tree_init($mytree, $myhtml2);

  return $mytree;
}

Originally, if we had performed the native call like:

sub myhtml_tree_init(
  TreeStruct,
  Native_MyHTML
) is native(&lib) returns int32 {*}

The code would SEGV instantly.

This has been misleading, because by chainging the signature to use Pointer instead of the native struct it exceptions out and the SEGV comes later (because of the exception, $!tree is not set!)

So why does this code SEGV if we use the latter form of the NativeCall?

I suspect there is something about the definition of TreeStruct.

So it turns out that we get a pointer for one of the parameters, and it stays there. Here is what seems to do the trick, but now the SEGV has moved somewhere else. There is another gist about this.

Here's the solution to the above issue, at least;

sub myhtml_tree_init(
  Pointer[TreeStruct],
  Native_MyHTML
) is native(&lib) returns int32 {*}

method new($myhtml) {
  my $mytree = myhtml_tree_create();
  say "tree created {$mytree}";
  my Native_MyHTML $myhtml2 .= new();
  say "myhtml2 created {$myhtml2}";
  say myhtml_tree_init($mytree, $myhtml2);

  return $mytree;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment