2 * Copyright (c) 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009,
3 * 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017
4 * mirabilos <m@mirbsd.org>
6 * Provided that these terms and disclaimer and all copyright notices
7 * are retained or reproduced in an accompanying document, permission
8 * is granted to deal in this work without restriction, including un-
9 * limited rights to use, publicly perform, distribute, sell, modify,
10 * merge, give away, or sublicence.
12 * This work is provided "AS IS" and WITHOUT WARRANTY of any kind, to
13 * the utmost extent permitted by applicable law, neither express nor
14 * implied; without malicious intent or gross negligence. In no event
15 * may a licensor, author or contributor be held liable for indirect,
16 * direct, other damage, loss, or other issues arising in any way out
17 * of dealing in the work, even if advised of the possibility of such
18 * damage or existence of a defect, except proven that it results out
19 * of said person's immediate fault when using the work as intended.
29 #define MKSH_CAT_BUFSIZ 256
35 #define ksh_sigmask(sig) (((sig) < 1 || (sig) > 127) ? 255 : 128 + (sig))
37 static char buf
[MKSH_CAT_BUFSIZ
];
38 static volatile sig_atomic_t intrsig
;
40 static const char Tsynerr
[] = "cat: syntax error\n";
41 static const char unkerr_msg
[] = "Unknown error";
42 static const char sigint_msg
[] = " ...\ncat: Interrupted\n";
45 disperr(const char *fn
)
50 write(2, fn
, strlen(fn
));
52 if (strerror_r(e
, buf
, MKSH_CAT_BUFSIZ
))
53 write(2, unkerr_msg
, sizeof(unkerr_msg
) - 1);
55 write(2, buf
, strlen(buf
));
60 sighandler(int signo
__attribute__((__unused__
)))
66 main(int argc
__attribute__((__unused__
)), char *wp
[])
70 const char *fn
= "<stdin>";
74 /* parse options (POSIX demands this) */
75 while ((cp
= *wp
) && *cp
++ == '-') {
78 if (cp
[0] == '-' && !cp
[1]) {
85 write(2, Tsynerr
, sizeof(Tsynerr
) - 1);
93 signal(SIGPIPE
, SIG_IGN
);
96 signal(SIGINT
, sighandler
);
101 if (fn
[0] == '-' && !fn
[1])
103 else if ((fd
= open(fn
, O_RDONLY
| O_BINARY
)) < 0) {
109 while (/* CONSTCOND */ 1) {
110 if ((n
= read(fd
, (cp
= buf
), MKSH_CAT_BUFSIZ
)) == -1) {
111 if (errno
== EINTR
) {
112 /* give the user a chance to ^C out */
115 /* interrupted, try again */
118 /* an error occured during reading */
123 /* end of file reached */
128 if ((w
= write(1, cp
, n
)) != -1) {
133 if (errno
== EINTR
) {
135 /* give the user a chance to ^C out */
138 sizeof(sigint_msg
) - 1);
139 return (ksh_sigmask(SIGINT
));
141 /* interrupted, try again */
144 if (errno
== EPIPE
) {
145 /* fake receiving signal */
146 rv
= ksh_sigmask(SIGPIPE
);
148 /* an error occured during writing */