/** *cr_attr_sel_destroy: *@a_this: the "this pointer" of the current *instance of #CRAttrSel. * *Destroys the current instance of #CRAttrSel. *Frees all the fields if they are non null. */ void cr_attr_sel_destroy (CRAttrSel * a_this) { g_return_if_fail (a_this); if (a_this->name) { cr_string_destroy (a_this->name); a_this->name = NULL; } if (a_this->value) { cr_string_destroy (a_this->value); a_this->value = NULL; } if (a_this->next) { cr_attr_sel_destroy (a_this->next); a_this->next = NULL; } if (a_this) { g_free (a_this); a_this = NULL; } }
/** * cr_declaration_destroy: *@a_this: the current instance of #CRDeclaration. * *Destructor of the declaration list. */ void cr_declaration_destroy (CRDeclaration * a_this) { CRDeclaration *cur = NULL; g_return_if_fail (a_this); /* *Go get the tail of the list. *Meanwhile, free each property/value pair contained in the list. */ for (cur = a_this; cur && cur->next; cur = cur->next) { if (cur->property) { cr_string_destroy (cur->property); cur->property = NULL; } if (cur->value) { cr_term_destroy (cur->value); cur->value = NULL; } } if (cur) { if (cur->property) { cr_string_destroy (cur->property); cur->property = NULL; } if (cur->value) { cr_term_destroy (cur->value); cur->value = NULL; } } /*in case the list contains only one element */ if (cur && !cur->prev) { g_free (cur); return; } /*walk backward the list and free each "next" element */ for (cur = cur->prev; cur && cur->prev; cur = cur->prev) { if (cur->next) { g_free (cur->next); cur->next = NULL; } } if (!cur) return; if (cur->next) { g_free (cur->next); cur->next = NULL; } g_free (cur); }
static void charset (CRDocHandler * a_this, CRString * a_charset, CRParsingLocation *a_location) { enum CRStatus status = CR_OK; CRStatement *stmt = NULL, *stmt2 = NULL; CRString *charset = NULL; ParsingContext *ctxt = NULL; ParsingContext **ctxtptr = NULL; g_return_if_fail (a_this); ctxtptr = &ctxt; status = cr_doc_handler_get_ctxt (a_this, (gpointer *) ctxtptr); g_return_if_fail (status == CR_OK && ctxt); g_return_if_fail (ctxt->stylesheet); charset = cr_string_dup (a_charset) ; stmt = cr_statement_new_at_charset_rule (ctxt->stylesheet, charset); g_return_if_fail (stmt); stmt2 = cr_statement_append (ctxt->stylesheet->statements, stmt); if (!stmt2) { if (stmt) { cr_statement_destroy (stmt); stmt = NULL; } if (charset) { cr_string_destroy (charset); } return; } ctxt->stylesheet->statements = stmt2; stmt2 = NULL; }
static void import_style (CRDocHandler * a_this, GList * a_media_list, CRString * a_uri, CRString * a_uri_default_ns, CRParsingLocation *a_location) { enum CRStatus status = CR_OK; CRString *uri = NULL; CRStatement *stmt = NULL, *stmt2 = NULL; ParsingContext *ctxt = NULL; ParsingContext **ctxtptr = NULL; GList *media_list = NULL ; g_return_if_fail (a_this); ctxtptr = &ctxt; status = cr_doc_handler_get_ctxt (a_this, (gpointer *) ctxtptr); g_return_if_fail (status == CR_OK && ctxt); g_return_if_fail (ctxt->stylesheet); uri = cr_string_dup (a_uri) ; if (a_media_list) media_list = cr_utils_dup_glist_of_cr_string (a_media_list) ; stmt = cr_statement_new_at_import_rule (ctxt->stylesheet, uri, media_list, NULL); if (!stmt) goto error; if (ctxt->cur_stmt) { stmt2 = cr_statement_append (ctxt->cur_stmt, stmt); if (!stmt2) goto error; ctxt->cur_stmt = stmt2; stmt2 = NULL; stmt = NULL; } else { stmt2 = cr_statement_append (ctxt->stylesheet->statements, stmt); if (!stmt2) goto error; ctxt->stylesheet->statements = stmt2; stmt2 = NULL; stmt = NULL; } return; error: if (uri) { cr_string_destroy (uri); } if (stmt) { cr_statement_destroy (stmt); stmt = NULL; } a_uri_default_ns = NULL; /*keep compiler happy */ }
/** * cr_pseudo_destroy: *@a_this: the current instance to destroy. * *destructor of the #CRPseudo class. */ void cr_pseudo_destroy (CRPseudo * a_this) { g_return_if_fail (a_this); if (a_this->name) { cr_string_destroy (a_this->name); a_this->name = NULL; } if (a_this->extra) { cr_string_destroy (a_this->extra); a_this->extra = NULL; } g_free (a_this); }
/** *Parses a text buffer that contains *a css declaration. * *@param a_statement the parent css2 statement of this *this declaration. Must be non NULL and of type *RULESET_STMT (must be a ruleset). *@param a_str the string that contains the statement. *@param a_enc the encoding of a_str. *@return the parsed declaration, or NULL in case of error. */ CRDeclaration * cr_declaration_parse_from_buf (CRStatement * a_statement, const guchar * a_str, enum CREncoding a_enc) { enum CRStatus status = CR_OK; CRTerm *value = NULL; CRString *property = NULL; CRDeclaration *result = NULL; gboolean important = FALSE; g_return_val_if_fail (a_str, NULL); if (a_statement) g_return_val_if_fail (a_statement->type == RULESET_STMT, NULL); CRParser *parser = (CRParser *) cr_parser_new_from_buf ((guchar*)a_str, strlen ((char *)a_str), a_enc, FALSE); g_return_val_if_fail (parser, NULL); status = cr_parser_try_to_skip_spaces_and_comments (parser); if (status != CR_OK) goto cleanup; status = cr_parser_parse_declaration (parser, &property, &value, &important); if (status != CR_OK || !property) goto cleanup; result = cr_declaration_new (a_statement, property, value); if (result) { property = NULL; value = NULL; result->important = important; } cleanup: if (parser) { cr_parser_destroy (parser); parser = NULL; } if (property) { cr_string_destroy (property); property = NULL; } if (value) { cr_term_destroy (value); value = NULL; } return result; }
static void cr_term_clear (CRTerm * a_this) { g_return_if_fail (a_this); switch (a_this->type) { case TERM_NUMBER: if (a_this->content.num) { cr_num_destroy (a_this->content.num); a_this->content.num = NULL; } break; case TERM_FUNCTION: if (a_this->ext_content.func_param) { cr_term_destroy (a_this->ext_content.func_param); a_this->ext_content.func_param = NULL; } case TERM_STRING: case TERM_IDENT: case TERM_URI: case TERM_HASH: if (a_this->content.str) { cr_string_destroy (a_this->content.str); a_this->content.str = NULL; } break; case TERM_RGB: if (a_this->content.rgb) { cr_rgb_destroy (a_this->content.rgb); a_this->content.rgb = NULL; } break; case TERM_UNICODERANGE: case TERM_NO_TYPE: default: break; } a_this->type = TERM_NO_TYPE; }
/** * cr_simple_sel_destroy: * *@a_this: the this pointer of the current instance of #CRSimpleSel. * *The destructor of the current instance of *#CRSimpleSel. Recursively calls the destructor of #CRSimpleSel->next */ void cr_simple_sel_destroy (CRSimpleSel * const a_this) { g_return_if_fail (a_this); if (a_this->name) { cr_string_destroy (a_this->name); a_this->name = NULL; } if (a_this->add_sel) { cr_additional_sel_destroy (a_this->add_sel); a_this->add_sel = NULL; } if (a_this->next) { cr_simple_sel_destroy (a_this->next); a_this->next = NULL; } g_free (a_this); }
/** *Frees the attributes of the current instance *of #CRtoken. *@param a_this the current instance of #CRToken. */ static void cr_token_clear (CRToken * a_this) { g_return_if_fail (a_this); switch (a_this->type) { case S_TK: case CDO_TK: case INCLUDES_TK: case DASHMATCH_TK: case PAGE_SYM_TK: case MEDIA_SYM_TK: case FONT_FACE_SYM_TK: case CHARSET_SYM_TK: case IMPORT_SYM_TK: case IMPORTANT_SYM_TK: case SEMICOLON_TK: case NO_TK: case DELIM_TK: case CBO_TK: case CBC_TK: case BO_TK: case BC_TK: break; case STRING_TK: case IDENT_TK: case HASH_TK: case URI_TK: case FUNCTION_TK: case COMMENT_TK: case ATKEYWORD_TK: if (a_this->u.str) { cr_string_destroy (a_this->u.str); a_this->u.str = NULL; } break; case EMS_TK: case EXS_TK: case LENGTH_TK: case ANGLE_TK: case TIME_TK: case FREQ_TK: case PERCENTAGE_TK: case NUMBER_TK: case PO_TK: case PC_TK: if (a_this->u.num) { cr_num_destroy (a_this->u.num); a_this->u.num = NULL; } break; case DIMEN_TK: if (a_this->u.num) { cr_num_destroy (a_this->u.num); a_this->u.num = NULL; } if (a_this->dimen) { cr_string_destroy (a_this->dimen); a_this->dimen = NULL; } break; case RGB_TK: if (a_this->u.rgb) { cr_rgb_destroy (a_this->u.rgb) ; a_this->u.rgb = NULL ; } break ; case UNICODERANGE_TK: /*not supported yet. */ break; default: cr_utils_trace_info ("I don't know how to clear this token\n") ; break; } a_this->type = NO_TK; }
/** * cr_declaration_parse_list_from_buf: *@a_str: the input buffer that contains the list of declaration to *parse. *@a_enc: the encoding of a_str * *Parses a ';' separated list of properties declaration. *Returns the parsed list of declaration, NULL if parsing failed. */ CRDeclaration * cr_declaration_parse_list_from_buf (const guchar * a_str, enum CREncoding a_enc) { enum CRStatus status = CR_OK; CRTerm *value = NULL; CRString *property = NULL; CRDeclaration *result = NULL, *cur_decl = NULL; CRParser *parser = NULL; CRTknzr *tokenizer = NULL; gboolean important = FALSE; g_return_val_if_fail (a_str, NULL); parser = cr_parser_new_from_buf ((guchar*)a_str, strlen (a_str), a_enc, FALSE); g_return_val_if_fail (parser, NULL); status = cr_parser_get_tknzr (parser, &tokenizer); if (status != CR_OK || !tokenizer) { if (status == CR_OK) status = CR_ERROR; goto cleanup; } status = cr_parser_try_to_skip_spaces_and_comments (parser); if (status != CR_OK) goto cleanup; status = cr_parser_parse_declaration (parser, &property, &value, &important); if (status != CR_OK || !property) { if (status != CR_OK) status = CR_ERROR; goto cleanup; } result = cr_declaration_new (NULL, property, value); if (result) { property = NULL; value = NULL; result->important = important; } /*now, go parse the other declarations */ for (;;) { guint32 c = 0; cr_parser_try_to_skip_spaces_and_comments (parser); status = cr_tknzr_peek_char (tokenizer, &c); if (status != CR_OK) { if (status == CR_END_OF_INPUT_ERROR) status = CR_OK; goto cleanup; } if (c == ';') { status = cr_tknzr_read_char (tokenizer, &c); } else { break; } important = FALSE; cr_parser_try_to_skip_spaces_and_comments (parser); status = cr_parser_parse_declaration (parser, &property, &value, &important); if (status != CR_OK || !property) { if (status == CR_END_OF_INPUT_ERROR) { status = CR_OK; } break; } cur_decl = cr_declaration_new (NULL, property, value); if (cur_decl) { cur_decl->important = important; result = cr_declaration_append (result, cur_decl); property = NULL; value = NULL; cur_decl = NULL; } else { break; } } cleanup: if (parser) { cr_parser_destroy (parser); parser = NULL; } if (property) { cr_string_destroy (property); property = NULL; } if (value) { cr_term_destroy (value); value = NULL; } if (status != CR_OK && result) { cr_declaration_destroy (result); result = NULL; } return result; }
/** *Parses a ';' separated list of properties declaration. *@param a_str the input buffer that contains the list of declaration to *parse. *@param a_enc the encoding of a_str *@return the parsed list of declaration, NULL if parsing failed. */ CRDeclaration * cr_declaration_parse_list_from_buf (const guchar * a_str, enum CREncoding a_enc) { enum CRStatus status = CR_OK; CRTerm *value = NULL; CRString *property = NULL; CRDeclaration *result = NULL, *cur_decl = NULL; CRTknzr *tokenizer = NULL; gboolean important = FALSE; g_return_val_if_fail (a_str, NULL); CRParser *parser = (CRParser *)cr_parser_new_from_buf ((guchar*)a_str, strlen ((char *)a_str), a_enc, FALSE); g_return_val_if_fail (parser, NULL); status = cr_parser_get_tknzr (parser, &tokenizer); if (status != CR_OK || !tokenizer) { if (status == CR_OK) status = CR_ERROR; goto cleanup; } status = cr_parser_try_to_skip_spaces_and_comments (parser); if (status != CR_OK) goto cleanup; status = cr_parser_parse_declaration (parser, &property, &value, &important); if (status != CR_OK || !property) { if (status != CR_OK) status = CR_ERROR; goto cleanup; } result = cr_declaration_new (NULL, property, value); if (result) { property = NULL; value = NULL; result->important = important; } /*now, go parse the other declarations */ for (;;) { guint32 c = 0; cr_parser_try_to_skip_spaces_and_comments (parser); status = cr_tknzr_peek_char (tokenizer, &c); if (status != CR_OK) { if (status == CR_END_OF_INPUT_ERROR) status = CR_OK; goto cleanup; } if (c == ';') { status = cr_tknzr_read_char (tokenizer, &c); } else { cr_tknzr_read_char (tokenizer, &c); continue; // try to keep reading until we reach the end or a ; } important = FALSE; cr_parser_try_to_skip_spaces_and_comments (parser); status = cr_parser_parse_declaration (parser, &property, &value, &important); if (status != CR_OK || !property) { if (status == CR_END_OF_INPUT_ERROR) { status = CR_OK; // simply the end of input, do not delete what we got so far, just finish break; } else { continue; // even if one declaration is broken, it's no reason to discard others (see http://www.w3.org/TR/CSS21/syndata.html#declaration) } } cur_decl = cr_declaration_new (NULL, property, value); if (cur_decl) { cur_decl->important = important; result = cr_declaration_append (result, cur_decl); property = NULL; value = NULL; cur_decl = NULL; } else { break; } } cleanup: if (parser) { cr_parser_destroy (parser); parser = NULL; } if (property) { cr_string_destroy (property); property = NULL; } if (value) { cr_term_destroy (value); value = NULL; } if (status != CR_OK && result) { cr_declaration_destroy (result); result = NULL; } return result; }