Subject: | [PATCH] Prevent creation of duplicate references |
Attached is a patch for 0.08 that prevents creating duplicate references in certain situations.
Without this patch, memory will quickly fill up when parsing multi-gigabyte files.
Tested with Perl 5.18.2 on x86_64 GNU/Linux 3.14.2.
(It's been a while since I wrote this, so hopefully I'm not forgetting anything.)
Subject: | Linux-DVB-DVBT-TS-0.08-referencefix.diff |
diff -ur Linux-DVB-DVBT-TS-0.08/xs/DVBT-ts.c Linux-DVB-DVBT-TS-0.08-modified-clean/xs/DVBT-ts.c
--- Linux-DVB-DVBT-TS-0.08/xs/DVBT-ts.c 2011-07-20 04:07:45.000000000 -0500
+++ Linux-DVB-DVBT-TS-0.08-modified-clean/xs/DVBT-ts.c 2013-03-16 15:26:01.508942843 -0500
@@ -1,5 +1,7 @@
# VERSION = "1.000"
+#define NEED_newRV_noinc
+#include "ppport.h"
# /*---------------------------------------------------------------------------------------------------*/
# /* Repair TS file */
@@ -214,7 +216,7 @@
dvb_error_clear() ;
/* Create Perl data */
- HVS(info_href, pids, newRV((SV *)pid_href)) ;
+ HVS(info_href, pids, newRV_noinc((SV *)pid_href)) ;
clear_settings(&settings) ;
if (settings_href)
@@ -251,7 +253,7 @@
_add_pesinfo(h, &piditem->pesinfo) ;
sprintf(key, "%d", piditem->pidinfo.pid) ;
- hv_store(pid_href, key, strlen(key), newRV((SV *)h), 0) ;
+ hv_store(pid_href, key, strlen(key), newRV_noinc((SV *)h), 0) ;
}
@@ -259,7 +261,7 @@
tsparse_end(tsreader) ;
}
- RETVAL = newRV((SV *)info_href);
+ RETVAL = newRV_noinc((SV *)info_href);
OUTPUT:
RETVAL
diff -ur Linux-DVB-DVBT-TS-0.08/xs/DVBT-ts-shared-c.c Linux-DVB-DVBT-TS-0.08-modified-clean/xs/DVBT-ts-shared-c.c
--- Linux-DVB-DVBT-TS-0.08/xs/DVBT-ts-shared-c.c 2011-07-15 06:51:40.000000000 -0500
+++ Linux-DVB-DVBT-TS-0.08-modified-clean/xs/DVBT-ts-shared-c.c 2013-03-16 19:13:37.369209860 -0500
@@ -12,6 +12,8 @@
#include <limits.h>
#include "ts_parse.h"
+#define NEED_newRV_noinc
+#include "../ppport.h"
#define DEBUG_TS
@@ -118,14 +120,14 @@
HVS_I(pidinfo_href, pidinfo, pid_error) ;
HVS_I(pidinfo_href, pidinfo, pktnum) ;
- HVS(info_href, pidinfo, newRV((SV *)pidinfo_href)) ;
+ HVS(info_href, pidinfo, newRV_noinc((SV *)pidinfo_href)) ;
}
//---------------------------------------------------------------------------------------------------------
static HV * _store_ts(HV * href, char *key, int64_t ts)
{
-HV * ts_href = newHV();
+HV * ts_href = (HV *)NULL;
unsigned secs, usecs ;
// 2^33 = 8589934592
@@ -133,6 +135,7 @@
if (ts >= 0)
{
+ ts_href = newHV();
secs = (unsigned)(ts / 90000) ;
usecs = (unsigned)((ts % 90000) * 1000 / 90) ;
@@ -142,7 +145,7 @@
sprintf(ts_str, "%"PRId64, ts) ;
HVS_STR(ts_href, ts, ts_str) ;
- hv_store(href, key, strlen(key), newRV((SV *)ts_href), 0) ;
+ hv_store(href, key, strlen(key), newRV_noinc((SV *)ts_href), 0) ;
}
return ts_href ;
@@ -159,18 +162,21 @@
{
// do the usual secs, usecs
ts_href = _store_ts(href, key, ts) ;
+
+ if (ts_href)
+ {
+ // now add HH:MM:SS
+ ss = (unsigned)(ts / 90000) ;
- // now add HH:MM:SS
- ss = (unsigned)(ts / 90000) ;
-
- hh = (unsigned)(ss / (60*60)) ;
- ss -= hh * 60*60 ;
- mm = (unsigned)(ss / (60)) ;
- ss -= mm * 60 ;
-
- HVS_INT(ts_href, hh, (int)hh) ;
- HVS_INT(ts_href, mm, (int)mm) ;
- HVS_INT(ts_href, ss, (int)ss) ;
+ hh = (unsigned)(ss / (60*60)) ;
+ ss -= hh * 60*60 ;
+ mm = (unsigned)(ss / (60)) ;
+ ss -= mm * 60 ;
+
+ HVS_INT(ts_href, hh, (int)hh) ;
+ HVS_INT(ts_href, mm, (int)mm) ;
+ HVS_INT(ts_href, ss, (int)ss) ;
+ }
}
}
@@ -203,7 +209,7 @@
}
HVS_STR(pesinfo_href, pes_psi, string) ;
- HVS(info_href, pesinfo, newRV((SV *)pesinfo_href)) ;
+ HVS(info_href, pesinfo, newRV_noinc((SV *)pesinfo_href)) ;
}
@@ -271,7 +277,7 @@
HVS_INT(error_href, code, (int)error_code) ;
error_str = dvb_error_str(error_code) ;
HVS_STR(error_href, str, error_str) ;
- HVS(info_href, error, newRV((SV *)error_href)) ;
+ HVS(info_href, error, newRV_noinc((SV *)error_href)) ;
PUSHMARK(SP);
@@ -279,7 +285,7 @@
sv_setref_pv(tsreader, "TSReaderPtr", (void *)hook_data->tsreader );
XPUSHs( tsreader );
- XPUSHs(sv_2mortal( newRV((SV *)info_href) ));
+ XPUSHs(sv_2mortal( newRV_noinc((SV *)info_href) ));
XPUSHs(hook_data->settings->perl_data);
PUTBACK;
@@ -361,7 +367,7 @@
sv_setref_pv(tsreader, "TSReaderPtr", (void *)hook_data->tsreader );
XPUSHs( tsreader );
- XPUSHs(sv_2mortal( newRV((SV *)info_href) ));
+ XPUSHs(sv_2mortal( newRV_noinc((SV *)info_href) ));
XPUSHs(sv_2mortal(newSVpv( (char *)packet, packet_len)));
XPUSHs(hook_data->settings->perl_data);
PUTBACK;
@@ -398,7 +404,7 @@
sv_setref_pv(tsreader, "TSReaderPtr", (void *)hook_data->tsreader );
XPUSHs( tsreader );
- XPUSHs(sv_2mortal( newRV((SV *)info_href) ));
+ XPUSHs(sv_2mortal( newRV_noinc((SV *)info_href) ));
XPUSHs(sv_2mortal(newSVpv( (char *)payload, payload_len)));
XPUSHs(hook_data->settings->perl_data);
PUTBACK;
@@ -437,7 +443,7 @@
sv_setref_pv(tsreader, "TSReaderPtr", (void *)hook_data->tsreader );
XPUSHs( tsreader );
- XPUSHs(sv_2mortal( newRV((SV *)info_href) ));
+ XPUSHs(sv_2mortal( newRV_noinc((SV *)info_href) ));
XPUSHs(sv_2mortal(newSVpv( (char *)pesdata, pesdata_len)));
XPUSHs(hook_data->settings->perl_data);
PUTBACK;
@@ -475,7 +481,7 @@
sv_setref_pv(tsreader, "TSReaderPtr", (void *)hook_data->tsreader );
XPUSHs( tsreader );
- XPUSHs(sv_2mortal( newRV((SV *)info_href) ));
+ XPUSHs(sv_2mortal( newRV_noinc((SV *)info_href) ));
XPUSHs(sv_2mortal(newSVpv( (char *)pesdata, pesdata_len)));
XPUSHs(hook_data->settings->perl_data);
PUTBACK;
@@ -518,7 +524,7 @@
sv_setref_pv(tsreader, "TSReaderPtr", (void *)hook_data->tsreader );
XPUSHs( tsreader );
- XPUSHs(sv_2mortal( newRV((SV *)info_href) ));
+ XPUSHs(sv_2mortal( newRV_noinc((SV *)info_href) ));
XPUSHs(sv_2mortal(newSViv( info->sequence->width )));
XPUSHs(sv_2mortal(newSViv( info->sequence->height )));
XPUSHs(sv_2mortal(newSVpv( (char *)info->display_fbuf->buf[0], datalen)));
@@ -562,7 +568,7 @@
sv_setref_pv(tsreader, "TSReaderPtr", (void *)hook_data->tsreader );
XPUSHs( tsreader );
- XPUSHs(sv_2mortal( newRV((SV *)info_href) ));
+ XPUSHs(sv_2mortal( newRV_noinc((SV *)info_href) ));
XPUSHs(sv_2mortal(newSViv( info->sequence->width )));
XPUSHs(sv_2mortal(newSViv( info->sequence->height )));
XPUSHs(sv_2mortal(newSVpv( (char *)info->display_fbuf->buf[0], datalen)));
@@ -607,7 +613,7 @@
sv_setref_pv(tsreader, "TSReaderPtr", (void *)hook_data->tsreader );
XPUSHs( tsreader );
- XPUSHs(sv_2mortal( newRV((SV *)info_href) ));
+ XPUSHs(sv_2mortal( newRV_noinc((SV *)info_href) ));
XPUSHs(sv_2mortal(newSVpv( (char *)info->audio, info->samples)));
XPUSHs(hook_data->settings->perl_data);
PUTBACK;