summaryrefslogtreecommitdiff
path: root/src/lib/libcrypto/bio/bss_file.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/lib/libcrypto/bio/bss_file.c')
-rw-r--r--src/lib/libcrypto/bio/bss_file.c109
1 files changed, 97 insertions, 12 deletions
diff --git a/src/lib/libcrypto/bio/bss_file.c b/src/lib/libcrypto/bio/bss_file.c
index 58fade9f29..0c8c8115fa 100644
--- a/src/lib/libcrypto/bio/bss_file.c
+++ b/src/lib/libcrypto/bio/bss_file.c
@@ -65,12 +65,34 @@
65#ifndef HEADER_BSS_FILE_C 65#ifndef HEADER_BSS_FILE_C
66#define HEADER_BSS_FILE_C 66#define HEADER_BSS_FILE_C
67 67
68#if defined(__linux) || defined(__sun) || defined(__hpux)
69/* Following definition aliases fopen to fopen64 on above mentioned
70 * platforms. This makes it possible to open and sequentially access
71 * files larger than 2GB from 32-bit application. It does not allow to
72 * traverse them beyond 2GB with fseek/ftell, but on the other hand *no*
73 * 32-bit platform permits that, not with fseek/ftell. Not to mention
74 * that breaking 2GB limit for seeking would require surgery to *our*
75 * API. But sequential access suffices for practical cases when you
76 * can run into large files, such as fingerprinting, so we can let API
77 * alone. For reference, the list of 32-bit platforms which allow for
78 * sequential access of large files without extra "magic" comprise *BSD,
79 * Darwin, IRIX...
80 */
81#ifndef _FILE_OFFSET_BITS
82#define _FILE_OFFSET_BITS 64
83#endif
84#endif
85
68#include <stdio.h> 86#include <stdio.h>
69#include <errno.h> 87#include <errno.h>
70#include "cryptlib.h" 88#include "cryptlib.h"
71#include <openssl/bio.h> 89#include "bio_lcl.h"
72#include <openssl/err.h> 90#include <openssl/err.h>
73 91
92#if defined(OPENSSL_SYS_NETWARE) && defined(NETWARE_CLIB)
93#include <nwfileio.h>
94#endif
95
74#if !defined(OPENSSL_NO_STDIO) 96#if !defined(OPENSSL_NO_STDIO)
75 97
76static int MS_CALLBACK file_write(BIO *h, const char *buf, int num); 98static int MS_CALLBACK file_write(BIO *h, const char *buf, int num);
@@ -110,8 +132,12 @@ BIO *BIO_new_file(const char *filename, const char *mode)
110 return(NULL); 132 return(NULL);
111 } 133 }
112 if ((ret=BIO_new(BIO_s_file_internal())) == NULL) 134 if ((ret=BIO_new(BIO_s_file_internal())) == NULL)
135 {
136 fclose(file);
113 return(NULL); 137 return(NULL);
138 }
114 139
140 BIO_clear_flags(ret,BIO_FLAGS_UPLINK); /* we did fopen -> we disengage UPLINK */
115 BIO_set_fp(ret,file,BIO_CLOSE); 141 BIO_set_fp(ret,file,BIO_CLOSE);
116 return(ret); 142 return(ret);
117 } 143 }
@@ -123,6 +149,7 @@ BIO *BIO_new_fp(FILE *stream, int close_flag)
123 if ((ret=BIO_new(BIO_s_file())) == NULL) 149 if ((ret=BIO_new(BIO_s_file())) == NULL)
124 return(NULL); 150 return(NULL);
125 151
152 BIO_set_flags(ret,BIO_FLAGS_UPLINK); /* redundant, left for documentation puposes */
126 BIO_set_fp(ret,stream,close_flag); 153 BIO_set_fp(ret,stream,close_flag);
127 return(ret); 154 return(ret);
128 } 155 }
@@ -137,6 +164,7 @@ static int MS_CALLBACK file_new(BIO *bi)
137 bi->init=0; 164 bi->init=0;
138 bi->num=0; 165 bi->num=0;
139 bi->ptr=NULL; 166 bi->ptr=NULL;
167 bi->flags=BIO_FLAGS_UPLINK; /* default to UPLINK */
140 return(1); 168 return(1);
141 } 169 }
142 170
@@ -147,8 +175,12 @@ static int MS_CALLBACK file_free(BIO *a)
147 { 175 {
148 if ((a->init) && (a->ptr != NULL)) 176 if ((a->init) && (a->ptr != NULL))
149 { 177 {
150 fclose((FILE *)a->ptr); 178 if (a->flags&BIO_FLAGS_UPLINK)
179 UP_fclose (a->ptr);
180 else
181 fclose (a->ptr);
151 a->ptr=NULL; 182 a->ptr=NULL;
183 a->flags=BIO_FLAGS_UPLINK;
152 } 184 }
153 a->init=0; 185 a->init=0;
154 } 186 }
@@ -161,8 +193,11 @@ static int MS_CALLBACK file_read(BIO *b, char *out, int outl)
161 193
162 if (b->init && (out != NULL)) 194 if (b->init && (out != NULL))
163 { 195 {
164 ret=fread(out,1,(int)outl,(FILE *)b->ptr); 196 if (b->flags&BIO_FLAGS_UPLINK)
165 if(ret == 0 && ferror((FILE *)b->ptr)) 197 ret=UP_fread(out,1,(int)outl,b->ptr);
198 else
199 ret=fread(out,1,(int)outl,(FILE *)b->ptr);
200 if(ret == 0 && (b->flags&BIO_FLAGS_UPLINK)?UP_ferror((FILE *)b->ptr):ferror((FILE *)b->ptr))
166 { 201 {
167 SYSerr(SYS_F_FREAD,get_last_sys_error()); 202 SYSerr(SYS_F_FREAD,get_last_sys_error());
168 BIOerr(BIO_F_FILE_READ,ERR_R_SYS_LIB); 203 BIOerr(BIO_F_FILE_READ,ERR_R_SYS_LIB);
@@ -178,7 +213,11 @@ static int MS_CALLBACK file_write(BIO *b, const char *in, int inl)
178 213
179 if (b->init && (in != NULL)) 214 if (b->init && (in != NULL))
180 { 215 {
181 if (fwrite(in,(int)inl,1,(FILE *)b->ptr)) 216 if (b->flags&BIO_FLAGS_UPLINK)
217 ret=UP_fwrite(in,(int)inl,1,b->ptr);
218 else
219 ret=fwrite(in,(int)inl,1,(FILE *)b->ptr);
220 if (ret)
182 ret=inl; 221 ret=inl;
183 /* ret=fwrite(in,1,(int)inl,(FILE *)b->ptr); */ 222 /* ret=fwrite(in,1,(int)inl,(FILE *)b->ptr); */
184 /* according to Tim Hudson <tjh@cryptsoft.com>, the commented 223 /* according to Tim Hudson <tjh@cryptsoft.com>, the commented
@@ -199,20 +238,45 @@ static long MS_CALLBACK file_ctrl(BIO *b, int cmd, long num, void *ptr)
199 { 238 {
200 case BIO_C_FILE_SEEK: 239 case BIO_C_FILE_SEEK:
201 case BIO_CTRL_RESET: 240 case BIO_CTRL_RESET:
202 ret=(long)fseek(fp,num,SEEK_SET); 241 if (b->flags&BIO_FLAGS_UPLINK)
242 ret=(long)UP_fseek(b->ptr,num,0);
243 else
244 ret=(long)fseek(fp,num,SEEK_SET);
203 break; 245 break;
204 case BIO_CTRL_EOF: 246 case BIO_CTRL_EOF:
205 ret=(long)feof(fp); 247 if (b->flags&BIO_FLAGS_UPLINK)
248 ret=(long)UP_feof(fp);
249 else
250 ret=(long)feof(fp);
206 break; 251 break;
207 case BIO_C_FILE_TELL: 252 case BIO_C_FILE_TELL:
208 case BIO_CTRL_INFO: 253 case BIO_CTRL_INFO:
209 ret=ftell(fp); 254 if (b->flags&BIO_FLAGS_UPLINK)
255 ret=UP_ftell(b->ptr);
256 else
257 ret=ftell(fp);
210 break; 258 break;
211 case BIO_C_SET_FILE_PTR: 259 case BIO_C_SET_FILE_PTR:
212 file_free(b); 260 file_free(b);
213 b->shutdown=(int)num&BIO_CLOSE; 261 b->shutdown=(int)num&BIO_CLOSE;
214 b->ptr=(char *)ptr; 262 b->ptr=ptr;
215 b->init=1; 263 b->init=1;
264#if BIO_FLAGS_UPLINK!=0
265#if defined(__MINGW32__) && defined(__MSVCRT__) && !defined(_IOB_ENTRIES)
266#define _IOB_ENTRIES 20
267#endif
268#if defined(_IOB_ENTRIES)
269 /* Safety net to catch purely internal BIO_set_fp calls */
270 if ((size_t)ptr >= (size_t)stdin &&
271 (size_t)ptr < (size_t)(stdin+_IOB_ENTRIES))
272 BIO_clear_flags(b,BIO_FLAGS_UPLINK);
273#endif
274#endif
275#ifdef UP_fsetmode
276 if (b->flags&BIO_FLAGS_UPLINK)
277 UP_fsetmode(b->ptr,num&BIO_FP_TEXT?'t':'b');
278 else
279#endif
216 { 280 {
217#if defined(OPENSSL_SYS_WINDOWS) 281#if defined(OPENSSL_SYS_WINDOWS)
218 int fd = fileno((FILE*)ptr); 282 int fd = fileno((FILE*)ptr);
@@ -220,6 +284,14 @@ static long MS_CALLBACK file_ctrl(BIO *b, int cmd, long num, void *ptr)
220 _setmode(fd,_O_TEXT); 284 _setmode(fd,_O_TEXT);
221 else 285 else
222 _setmode(fd,_O_BINARY); 286 _setmode(fd,_O_BINARY);
287#elif defined(OPENSSL_SYS_NETWARE) && defined(NETWARE_CLIB)
288 int fd = fileno((FILE*)ptr);
289 /* Under CLib there are differences in file modes
290 */
291 if (num & BIO_FP_TEXT)
292 setmode(fd,O_TEXT);
293 else
294 setmode(fd,O_BINARY);
223#elif defined(OPENSSL_SYS_MSDOS) 295#elif defined(OPENSSL_SYS_MSDOS)
224 int fd = fileno((FILE*)ptr); 296 int fd = fileno((FILE*)ptr);
225 /* Set correct text/binary mode */ 297 /* Set correct text/binary mode */
@@ -272,6 +344,12 @@ static long MS_CALLBACK file_ctrl(BIO *b, int cmd, long num, void *ptr)
272 else 344 else
273 strcat(p,"t"); 345 strcat(p,"t");
274#endif 346#endif
347#if defined(OPENSSL_SYS_NETWARE)
348 if (!(num & BIO_FP_TEXT))
349 strcat(p,"b");
350 else
351 strcat(p,"t");
352#endif
275 fp=fopen(ptr,p); 353 fp=fopen(ptr,p);
276 if (fp == NULL) 354 if (fp == NULL)
277 { 355 {
@@ -281,8 +359,9 @@ static long MS_CALLBACK file_ctrl(BIO *b, int cmd, long num, void *ptr)
281 ret=0; 359 ret=0;
282 break; 360 break;
283 } 361 }
284 b->ptr=(char *)fp; 362 b->ptr=fp;
285 b->init=1; 363 b->init=1;
364 BIO_clear_flags(b,BIO_FLAGS_UPLINK); /* we did fopen -> we disengage UPLINK */
286 break; 365 break;
287 case BIO_C_GET_FILE_PTR: 366 case BIO_C_GET_FILE_PTR:
288 /* the ptr parameter is actually a FILE ** in this case. */ 367 /* the ptr parameter is actually a FILE ** in this case. */
@@ -299,7 +378,10 @@ static long MS_CALLBACK file_ctrl(BIO *b, int cmd, long num, void *ptr)
299 b->shutdown=(int)num; 378 b->shutdown=(int)num;
300 break; 379 break;
301 case BIO_CTRL_FLUSH: 380 case BIO_CTRL_FLUSH:
302 fflush((FILE *)b->ptr); 381 if (b->flags&BIO_FLAGS_UPLINK)
382 UP_fflush(b->ptr);
383 else
384 fflush((FILE *)b->ptr);
303 break; 385 break;
304 case BIO_CTRL_DUP: 386 case BIO_CTRL_DUP:
305 ret=1; 387 ret=1;
@@ -321,7 +403,10 @@ static int MS_CALLBACK file_gets(BIO *bp, char *buf, int size)
321 int ret=0; 403 int ret=0;
322 404
323 buf[0]='\0'; 405 buf[0]='\0';
324 fgets(buf,size,(FILE *)bp->ptr); 406 if (bp->flags&BIO_FLAGS_UPLINK)
407 UP_fgets(buf,size,bp->ptr);
408 else
409 fgets(buf,size,(FILE *)bp->ptr);
325 if (buf[0] != '\0') 410 if (buf[0] != '\0')
326 ret=strlen(buf); 411 ret=strlen(buf);
327 return(ret); 412 return(ret);