xref: /plan9/sys/src/cmd/gs/src/gp_dosfs.c (revision 593dc095aefb2a85c828727bbfa9da139a49bdf4)
1 /* Copyright (C) 1992, 1993, 1996, 1998 Aladdin Enterprises.  All rights reserved.
2 
3   This software is provided AS-IS with no warranty, either express or
4   implied.
5 
6   This software is distributed under license and may not be copied,
7   modified or distributed except as expressly authorized under the terms
8   of the license contained in the file LICENSE in this distribution.
9 
10   For more information about licensing, please refer to
11   http://www.ghostscript.com/licensing/. For information on
12   commercial licensing, go to http://www.artifex.com/licensing/ or
13   contact Artifex Software, Inc., 101 Lucas Valley Road #110,
14   San Rafael, CA  94903, U.S.A., +1(415)492-9861.
15 */
16 
17 /* $Id: gp_dosfs.c,v 1.17 2004/04/08 16:18:25 giles Exp $ */
18 /* Common routines for MS-DOS (any compiler) and DesqView/X, */
19 /* which has a MS-DOS-like file system. */
20 #include "dos_.h"
21 #include "gx.h"
22 #include "gp.h"
23 #include "gpmisc.h"
24 
25 /* ------ Printer accessing ------ */
26 
27 /* Put a printer file (which might be stdout) into binary or text mode. */
28 /* This is not a standard gp procedure, */
29 /* but all MS-DOS configurations need it. */
30 void
gp_set_file_binary(int prnfno,bool binary)31 gp_set_file_binary(int prnfno, bool binary)
32 {
33     union REGS regs;
34 
35     regs.h.ah = 0x44;		/* ioctl */
36     regs.h.al = 0;		/* get device info */
37     regs.rshort.bx = prnfno;
38     intdos(&regs, &regs);
39     if (regs.rshort.cflag != 0 || !(regs.h.dl & 0x80))
40 	return;			/* error, or not a device */
41     if (binary)
42 	regs.h.dl |= 0x20;	/* binary (no ^Z intervention) */
43     else
44 	regs.h.dl &= ~0x20;	/* text */
45     regs.h.dh = 0;
46     regs.h.ah = 0x44;		/* ioctl */
47     regs.h.al = 1;		/* set device info */
48     intdos(&regs, &regs);
49 }
50 
51 /* ------ File accessing ------ */
52 
53 /* Set a file into binary or text mode. */
54 int
gp_setmode_binary(FILE * pfile,bool binary)55 gp_setmode_binary(FILE * pfile, bool binary)
56 {
57     gp_set_file_binary(fileno(pfile), binary);
58     return 0;			/* Fake out dos return status */
59 }
60 
61 /* ------ File names ------ */
62 
63 /* Define the character used for separating file names in a list. */
64 const char gp_file_name_list_separator = ';';
65 
66 /* Define the string to be concatenated with the file mode */
67 /* for opening files without end-of-line conversion. */
68 const char gp_fmode_binary_suffix[] = "b";
69 
70 /* Define the file modes for binary reading or writing. */
71 const char gp_fmode_rb[] = "rb";
72 const char gp_fmode_wb[] = "wb";
73 
74 /* -------------- Helpers for gp_file_name_combine_generic ------------- */
75 
gp_file_name_root(const char * fname,uint len)76 uint gp_file_name_root(const char *fname, uint len)
77 {   int i = 0;
78 
79     if (len == 0)
80 	return 0;
81     if (len > 1 && fname[0] == '\\' && fname[1] == '\\') {
82 	/* A network path: "\\server\share\" */
83 	int k = 0;
84 
85 	for (i = 2; i < len; i++)
86 	    if (fname[i] == '\\' || fname[i] == '/')
87 		if (k++) {
88 		    i++;
89 		    break;
90 		}
91     } else if (fname[0] == '/' || fname[0] == '\\') {
92 	/* Absolute with no drive. */
93 	i = 1;
94     } else if (len > 1 && fname[1] == ':') {
95 	/* Absolute with a drive. */
96 	i = (len > 2 && (fname[2] == '/' || fname[2] == '\\') ? 3 : 2);
97     }
98     return i;
99 }
100 
gs_file_name_check_separator(const char * fname,int len,const char * item)101 uint gs_file_name_check_separator(const char *fname, int len, const char *item)
102 {   if (len > 0) {
103 	if (fname[0] == '/' || fname[0] == '\\')
104 	    return 1;
105     } else if (len < 0) {
106 	if (fname[-1] == '/' || fname[-1] == '\\')
107 	    return 1;
108     }
109     return 0;
110 }
111 
gp_file_name_is_parent(const char * fname,uint len)112 bool gp_file_name_is_parent(const char *fname, uint len)
113 {   return len == 2 && fname[0] == '.' && fname[1] == '.';
114 }
115 
gp_file_name_is_current(const char * fname,uint len)116 bool gp_file_name_is_current(const char *fname, uint len)
117 {   return len == 1 && fname[0] == '.';
118 }
119 
gp_file_name_separator(void)120 const char *gp_file_name_separator(void)
121 {   return "/";
122 }
123 
gp_file_name_directory_separator(void)124 const char *gp_file_name_directory_separator(void)
125 {   return "/";
126 }
127 
gp_file_name_parent(void)128 const char *gp_file_name_parent(void)
129 {   return "..";
130 }
131 
gp_file_name_current(void)132 const char *gp_file_name_current(void)
133 {   return ".";
134 }
135 
gp_file_name_is_partent_allowed(void)136 bool gp_file_name_is_partent_allowed(void)
137 {   return true;
138 }
139 
gp_file_name_is_empty_item_meanful(void)140 bool gp_file_name_is_empty_item_meanful(void)
141 {   return false;
142 }
143 
144 gp_file_name_combine_result
gp_file_name_combine(const char * prefix,uint plen,const char * fname,uint flen,bool no_sibling,char * buffer,uint * blen)145 gp_file_name_combine(const char *prefix, uint plen, const char *fname, uint flen,
146 		    bool no_sibling, char *buffer, uint *blen)
147 {
148     return gp_file_name_combine_generic(prefix, plen,
149 	    fname, flen, no_sibling, buffer, blen);
150 }
151