This is a live mirror of the Perl 5 development currently hosted at https://github.com/perl/perl5
perl 5.0 alpha 4
[perl5.git] / usersub.c
1 /* $RCSfile: usersub.c,v $$Revision: 4.1 $$Date: 92/08/07 18:28:45 $
2  *
3  *  This file contains stubs for routines that the user may define to
4  *  set up glue routines for C libraries or to decrypt encrypted scripts
5  *  for execution.
6  *
7  * $Log:        usersub.c,v $
8  * Revision 4.1  92/08/07  18:28:45  lwall
9  * 
10  * Revision 4.0.1.2  92/06/08  16:04:24  lwall
11  * patch20: removed implicit int declarations on functions
12  * 
13  * Revision 4.0.1.1  91/11/11  16:47:17  lwall
14  * patch19: deleted some unused functions from usersub.c
15  * 
16  * Revision 4.0  91/03/20  01:55:56  lwall
17  * 4.0 baseline.
18  * 
19  */
20
21 #include "EXTERN.h"
22 #include "perl.h"
23
24 int
25 userinit()
26 {
27     return 0;
28 }
29
30 /*
31  * The following is supplied by John Macdonald as a means of decrypting
32  * and executing (presumably proprietary) scripts that have been encrypted
33  * by a (presumably secret) method.  The idea is that you supply your own
34  * routine in place of cryptfilter (which is purposefully a very weak
35  * encryption).  If an encrypted script is detected, a process is forked
36  * off to run the cryptfilter routine as input to perl.
37  */
38
39 #ifdef CRYPTSCRIPT
40
41 #include <signal.h>
42 #ifdef I_VFORK
43 #include <vfork.h>
44 #endif
45
46 #ifdef CRYPTLOCAL
47
48 #include "cryptlocal.h"
49
50 #else   /* ndef CRYPTLOCAL */
51
52 #define CRYPT_MAGIC_1   0xfb
53 #define CRYPT_MAGIC_2   0xf1
54
55 void
56 cryptfilter( fil )
57 FILE *  fil;
58 {
59     int    ch;
60
61     while( (ch = getc( fil )) != EOF ) {
62         putchar( (ch ^ 0x80) );
63     }
64 }
65
66 #endif  /* CRYPTLOCAL */
67
68 #ifndef MSDOS
69 static FILE     *lastpipefile;
70 static int      pipepid;
71
72 #ifdef VOIDSIG
73 #  define       VOID    void
74 #else
75 #  define       VOID    int
76 #endif
77
78 FILE *
79 my_pfiopen(fil,func)            /* open a pipe to function call for input */
80 FILE    *fil;
81 VOID    (*func)();
82 {
83     int p[2];
84     SV *sv;
85
86     if (pipe(p) < 0) {
87         fclose( fil );
88         croak("Can't get pipe for decrypt");
89     }
90
91     /* make sure that the child doesn't get anything extra */
92     fflush(stdout);
93     fflush(stderr);
94
95     while ((pipepid = fork()) < 0) {
96         if (errno != EAGAIN) {
97             close(p[0]);
98             close(p[1]);
99             fclose( fil );
100             croak("Can't fork for decrypt");
101         }
102         sleep(5);
103     }
104     if (pipepid == 0) {
105         close(p[0]);
106         if (p[1] != 1) {
107             dup2(p[1], 1);
108             close(p[1]);
109         }
110         (*func)(fil);
111         fflush(stdout);
112         fflush(stderr);
113         _exit(0);
114     }
115     close(p[1]);
116     close(fileno(fil));
117     fclose(fil);
118     sv = *av_fetch(fdpid,p[0],TRUE);
119     sv->sv_u.sv_useful = pipepid;
120     return fdopen(p[0], "r");
121 }
122
123 void
124 cryptswitch()
125 {
126     int ch;
127 #ifdef STDSTDIO
128     /* cheat on stdio if possible */
129     if (rsfp->_cnt > 0 && (*rsfp->_ptr & 0xff) != CRYPT_MAGIC_1)
130         return;
131 #endif
132     ch = getc(rsfp);
133     if (ch == CRYPT_MAGIC_1) {
134         if (getc(rsfp) == CRYPT_MAGIC_2) {
135             if( perldb ) croak("can't debug an encrypted script");
136             rsfp = my_pfiopen( rsfp, cryptfilter );
137             preprocess = 1;     /* force call to pclose when done */
138         }
139         else
140             croak( "bad encryption run_format" );
141     }
142     else
143         ungetc(ch,rsfp);
144 }
145 #endif /* !MSDOS */
146
147 #endif /* CRYPTSCRIPT */