Front page | perl.perl5.porters |
Postings from February 2006
Re: possibly (tiny) size saving idea
Thread Previous
|
Thread Next
From:
Nicholas Clark
Date:
February 3, 2006 05:10
Subject:
Re: possibly (tiny) size saving idea
Message ID:
20060203130955.GY616@plum.flirble.org
On Sat, Jan 28, 2006 at 08:04:38PM +0000, Nick Ing-Simmons wrote:
> Nicholas Clark <nick@ccl4.org> writes:
> >As far as I can tell, the rest of the code won't notice if that array is
> >malloc()ed and resized as needed. From what I remember, that would add no
> >significant complexity to the code.
>
> It is global so that all threads and pseudo-forks can see it.
> It isn't malloc-ed just because the Win32/PerlHost "per-thread" malloc
> got in the way. It is possible that the global malloc pool could be used.
Well, I committed it as change 27059, so lets see if it works.
Nicholas Clark
Change 27059 by nicholas@nicholas-saigo on 2006/02/03 13:06:00
Change PL_perlio_fd_refcnt from a fixed size static array to a pointer
to a dynamic array.
Affected files ...
... //depot/perl/embedvar.h#213 edit
... //depot/perl/perlapi.h#135 edit
... //depot/perl/perlio.c#300 edit
... //depot/perl/perlvars.h#67 edit
Differences ...
==== //depot/perl/embedvar.h#213 (text+w) ====
@@ -882,6 +882,8 @@
#define PL_Gperlio_debug_fd (my_vars->Gperlio_debug_fd)
#define PL_perlio_fd_refcnt (my_vars->Gperlio_fd_refcnt)
#define PL_Gperlio_fd_refcnt (my_vars->Gperlio_fd_refcnt)
+#define PL_perlio_fd_refcnt_size (my_vars->Gperlio_fd_refcnt_size)
+#define PL_Gperlio_fd_refcnt_size (my_vars->Gperlio_fd_refcnt_size)
#define PL_ppaddr (my_vars->Gppaddr)
#define PL_Gppaddr (my_vars->Gppaddr)
#define PL_sh_path (my_vars->Gsh_path)
@@ -931,6 +933,7 @@
#define PL_Gpatleave PL_patleave
#define PL_Gperlio_debug_fd PL_perlio_debug_fd
#define PL_Gperlio_fd_refcnt PL_perlio_fd_refcnt
+#define PL_Gperlio_fd_refcnt_size PL_perlio_fd_refcnt_size
#define PL_Gppaddr PL_ppaddr
#define PL_Gsh_path PL_sh_path
#define PL_Gsig_defaulting PL_sig_defaulting
==== //depot/perl/perlapi.h#135 (text+w) ====
@@ -946,6 +946,8 @@
#define PL_perlio_debug_fd (*Perl_Gperlio_debug_fd_ptr(NULL))
#undef PL_perlio_fd_refcnt
#define PL_perlio_fd_refcnt (*Perl_Gperlio_fd_refcnt_ptr(NULL))
+#undef PL_perlio_fd_refcnt_size
+#define PL_perlio_fd_refcnt_size (*Perl_Gperlio_fd_refcnt_size_ptr(NULL))
#undef PL_ppaddr
#define PL_ppaddr (*Perl_Gppaddr_ptr(NULL))
#undef PL_sh_path
==== //depot/perl/perlio.c#300 (text) ====
@@ -56,8 +56,6 @@
#include "XSUB.h"
-#define PERLIO_MAX_REFCOUNTABLE_FD 2048
-
#ifdef __Lynx__
/* Missing proto on LynxOS */
int mkstemp(char*);
@@ -2247,6 +2245,42 @@
/* PL_perlio_fd_refcnt[] is in intrpvar.h */
+/* Must be called with PerlIO_mutex locked. */
+static void
+S_more_refcounted_fds(pTHX_ const int new_fd) {
+ const int old_max = PL_perlio_fd_refcnt_size;
+ const int new_max = 16 + (new_fd & 15);
+ int *new_array;
+
+ PerlIO_debug("More fds - old=%d, need %d, new=%d\n",
+ old_max, new_fd, new_max);
+
+ if (new_fd < old_max) {
+ return;
+ }
+
+ new_array
+ = PerlMemShared_realloc(PL_perlio_fd_refcnt, new_max * sizeof(int));
+
+ if (!new_array) {
+#ifdef USE_THREADS
+ MUTEX_UNLOCK(&PerlIO_mutex);
+#endif
+ /* Can't use PerlIO to write as it allocates memory */
+ PerlLIO_write(PerlIO_fileno(Perl_error_log),
+ PL_no_mem, strlen(PL_no_mem));
+ my_exit(1);
+ }
+
+ PL_perlio_fd_refcnt_size = new_max;
+ PL_perlio_fd_refcnt = new_array;
+
+ PerlIO_debug("Zeroing %p, %d\n", new_array + old_max, new_max - old_max);
+
+ Zero(new_array + old_max, new_max - old_max, int);
+}
+
+
void
PerlIO_init(pTHX)
{
@@ -2260,13 +2294,18 @@
PerlIOUnix_refcnt_inc(int fd)
{
dTHX;
- if (fd >= 0 && fd < PERLIO_MAX_REFCOUNTABLE_FD) {
+ if (fd >= 0) {
dVAR;
+
#ifdef USE_THREADS
MUTEX_LOCK(&PerlIO_mutex);
#endif
+ if (fd >= PL_perlio_fd_refcnt_size)
+ S_more_refcounted_fds(aTHX_ fd);
+
PL_perlio_fd_refcnt[fd]++;
PerlIO_debug("fd %d refcnt=%d\n",fd,PL_perlio_fd_refcnt[fd]);
+
#ifdef USE_THREADS
MUTEX_UNLOCK(&PerlIO_mutex);
#endif
@@ -2278,11 +2317,16 @@
{
dTHX;
int cnt = 0;
- if (fd >= 0 && fd < PERLIO_MAX_REFCOUNTABLE_FD) {
+ if (fd >= 0) {
dVAR;
#ifdef USE_THREADS
MUTEX_LOCK(&PerlIO_mutex);
#endif
+ /* XXX should this be a panic? */
+ if (fd >= PL_perlio_fd_refcnt_size)
+ S_more_refcounted_fds(aTHX_ fd);
+
+ /* XXX should this be a panic if it drops below 0? */
cnt = --PL_perlio_fd_refcnt[fd];
PerlIO_debug("fd %d refcnt=%d\n",fd,cnt);
#ifdef USE_THREADS
@@ -2512,7 +2556,7 @@
if (flags & PERLIO_DUP_FD) {
fd = PerlLIO_dup(fd);
}
- if (fd >= 0 && fd < PERLIO_MAX_REFCOUNTABLE_FD) {
+ if (fd >= 0) {
f = PerlIOBase_dup(aTHX_ f, o, param, flags);
if (f) {
/* If all went well overwrite fd in dup'ed lay with the dup()'ed fd */
==== //depot/perl/perlvars.h#67 (text) ====
@@ -76,7 +76,8 @@
#endif
#ifdef USE_PERLIO
-PERLVARA(Gperlio_fd_refcnt, 2048, int) /* PERLIO_MAX_REFCOUNTABLE_FD */
+PERLVARI(Gperlio_fd_refcnt, int*, 0) /* Pointer to array of fd refcounts. */
+PERLVARI(Gperlio_fd_refcnt_size, int, 0) /* Size of the array */
PERLVARI(Gperlio_debug_fd, int, 0) /* the fd to write perlio debug into, 0 means not set yet */
#endif
Thread Previous
|
Thread Next