MODULE = Mail::Rspamd PACKAGE = Mail::Rspamd::Hash::Header PREFIX=hash_ Mail::Rspamd::Hash::Header hash_TIEHASH (Class, objptr) char * Class Mail::Rspamd::Message objptr PREINIT: hash_header * hash; CODE: hash = g_malloc (sizeof (hash_header)); hash->keyindex = 0; hash->objptr = objptr; hash->fetchvalue = NULL; RETVAL = hash; OUTPUT: RETVAL void hash_DESTROY (obj) Mail::Rspamd::Hash::Header obj CODE: obj->objptr = NULL; g_free (obj); void hash_FETCH (obj, key) Mail::Rspamd::Hash::Header obj const char * key PREINIT: Mail__Rspamd__Message msg; GList *gret = NULL, *item; AV * retav; I32 gimme = GIMME_V; PPCODE: msg = obj->objptr; /* THE HACK - FETCH method would get value indirectly from NEXTKEY */ if (obj->keyindex != -1 && obj->fetchvalue != NULL) { XPUSHs (sv_2mortal (newSVpv (obj->fetchvalue, 0))); obj->fetchvalue == NULL; XSRETURN(1); } obj->fetchvalue = NULL; gret = message_get_header (NULL, msg, key); if (!gret || gret->data == NULL) { if (gret) { g_list_free(gret); } XSRETURN(0); } else { if (gret->next == NULL) { // one value XPUSHs (sv_2mortal (newSVpv ((char *)(gret->data), 0))); } else { if (gimme == G_ARRAY) { item = gret; while (item && item->data) { XPUSHs (sv_2mortal (newSVpv ((char *)(item->data), 0))); item = item->next; } } else if (gimme == G_SCALAR) { retav = newAV(); item = gret; while (item && item->data) { av_push (retav, newSVpv ((char *)g_strdup ((item->data)), 0)); item = item->next; } XPUSHs (newRV_noinc ((SV *)retav)); } } } if (gret) { item = gret; while (item) { if (item->data) { g_free((char *)(item->data)); } item = item->next; } g_list_free(gret); } void hash_STORE (obj, key, svmixed) Mail::Rspamd::Hash::Header obj const char * key SV * svmixed PREINIT: Mail__Rspamd__Message msg; char * value; SV * svvalue; svtype svvaltype; STRLEN vallen; CODE: /* only one value can be stored - no arrays allowed by perl */ msg = obj->objptr; svvalue = svmixed; if (SvROK (svmixed)) { svvalue = SvRV(svmixed); } svvaltype = SvTYPE (svvalue); if (SvGMAGICAL(svvalue)) { mg_get(svvalue); } /* delete header for the first array item */ g_mime_object_remove_header (GMIME_OBJECT(msg), key); if (svvaltype == SVt_PVAV) { AV * avvalue; I32 i, avlen; SV * svtmp; /* set header */ avvalue = (AV *)svvalue; avlen = av_len(avvalue); for (i=avlen; i>=0; --i) { svtmp = (SV *)(*(av_fetch (avvalue, i, 0))); if (SvGMAGICAL(svtmp)) { mg_get(svtmp); } if (svtmp && SvPOKp(svtmp)) { value = (char *)SvPV(svtmp, vallen); message_set_header (msg, key, value); } } } else if (SvPOK(svvalue) || SvIOK(svvalue) || SvNOK(svvalue)) { value = (char *)SvPV (svvalue, vallen); message_set_header (msg, key, value); } else { /* assume scalar value */ /* undefined value -> remove header */ if (!(SvOK(svvalue))) { g_mime_object_remove_header (GMIME_OBJECT(msg), key); } } gboolean hash_EXISTS (obj, key) Mail::Rspamd::Hash::Header obj const char * key PREINIT: Mail__Rspamd__Message msg; GList *gret, *item; CODE: msg = obj->objptr; gret = message_get_header (NULL, msg, key); RETVAL = (gret != NULL && gret->data != NULL); if (gret) { item = gret; while (item) { if (item->data) { g_free((char *)(item->data)); } item = item->next; } g_list_free(gret); } OUTPUT: RETVAL void hash_DELETE(obj, key) Mail::Rspamd::Hash::Header obj const char * key CODE: g_mime_object_remove_header (GMIME_OBJECT(obj->objptr), key); void hash_NEXTKEY(obj, lastkey = NULL) Mail::Rspamd::Hash::Header obj const char * lastkey ALIAS: Mail::Rspamd::Hash::Header::FIRSTKEY = 1 PREINIT: const char * key = NULL; const char * value = NULL; Mail__Rspamd__Message msg; I32 gimme = GIMME_V; gint i, j, found; #ifdef GMIME24 GMimeHeaderList *hl; GMimeHeaderIter *iter; #else local_GMimeHeader * header; #endif struct raw_header *h; INIT: if (ix == 1) { obj->keyindex = -1; } PPCODE: msg = obj->objptr; ++obj->keyindex; i = obj->keyindex; #ifdef GMIME24 hl = g_mime_object_get_header_list (GMIME_OBJECT (msg)); j = 0; found = 0; if (g_mime_header_list_get_iter (hl, iter)) { while (g_mime_header_iter_is_valid (iter)) { if (j >= i) { key = g_mime_header_iter_get_name (iter); value = g_mime_header_iter_get_value (iter); found = 1; break; } if (!g_mime_header_iter_next (iter)) { break; } } } #else header = GMIME_OBJECT(msg)->headers; h = header->headers; j = 0; found = 0; while (h) { if (j >= i) { key = h->name; value = h->value; found = 1; break; } j++; h = h->next; } #endif if (!found && key == NULL) { obj->keyindex = -1; } /* THE HACK - FETCH method would get value indirectly */ obj->fetchvalue = NULL; if (key) { XPUSHs (sv_2mortal (newSVpv (key, 0))); if (gimme != G_SCALAR && value) { XPUSHs (sv_2mortal (newSVpv (value, 0))); } /* THE HACK - FETCH method would get value indirectly */ obj->fetchvalue = (char *)value; } #ifndef GMIME24 void hash_CLEAR(obj) Mail::Rspamd::Hash::Header obj PREINIT: Mail__Rspamd__Message message; local_GMimeHeader *header; CODE: message = obj->objptr; g_free (message->from); message->from = NULL; g_free (message->reply_to); message->reply_to = NULL; /* destroy all recipients */ g_hash_table_foreach_remove (message->recipients, recipients_destroy, NULL); g_free (message->subject); message->subject = NULL; g_free (message->message_id); message->message_id = NULL; /* free all the headers */ header = GMIME_OBJECT(message)->headers; g_mime_header_destroy (header); GMIME_OBJECT(message)->headers = g_mime_header_new (); #endif