aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDenis Vlasenko <vda.linux@googlemail.com>2008-02-25 14:48:15 +0000
committerDenis Vlasenko <vda.linux@googlemail.com>2008-02-25 14:48:15 +0000
commit38b8831b3201a9e44cfb156b5b8577e4f5e8d761 (patch)
treedafba8c135d54704bc8747cabadc722a98a68a01
parentf99afb5dff00534df6cf8f4d9de5d274c7818eac (diff)
downloadbusybox-w32-38b8831b3201a9e44cfb156b5b8577e4f5e8d761.tar.gz
busybox-w32-38b8831b3201a9e44cfb156b5b8577e4f5e8d761.tar.bz2
busybox-w32-38b8831b3201a9e44cfb156b5b8577e4f5e8d761.zip
lpd: now with "svn add"...
-rw-r--r--printutils/lpd.c79
1 files changed, 79 insertions, 0 deletions
diff --git a/printutils/lpd.c b/printutils/lpd.c
new file mode 100644
index 000000000..ed3d9d100
--- /dev/null
+++ b/printutils/lpd.c
@@ -0,0 +1,79 @@
1/* vi: set sw=4 ts=4: */
2/*
3 * micro lpd - a small non-queueing lpd
4 *
5 * Copyright (C) 2008 by Vladimir Dronnikov <dronnikov@gmail.com>
6 *
7 * Licensed under GPLv2, see file LICENSE in this tarball for details.
8 */
9#include "libbb.h"
10
11int lpd_main(int argc, char *argv[]) MAIN_EXTERNALLY_VISIBLE;
12int lpd_main(int argc, char *argv[])
13{
14 char *s;
15
16 // goto spool directory
17 // spool directory contains either links to real printer devices or just simple files
18 // these links or files are called "queues"
19 if (!argv[1])
20 bb_show_usage();
21
22 xchdir(argv[1]);
23
24 xdup2(1, 2);
25
26 // read command
27 s = xmalloc_reads(STDIN_FILENO, NULL);
28
29 // N.B. we keep things simple
30 // only "receive job" command is meaningful here...
31 if (2 == *s) {
32 char *queue;
33
34 // parse command: "\x2QUEUE_NAME\n"
35 queue = s + 1;
36 *strchrnul(s, '\n') = '\0';
37
38 while (1) {
39 // signal OK
40 write(STDOUT_FILENO, "", 1);
41 // get subcommand
42 s = xmalloc_reads(STDIN_FILENO, NULL);
43 if (!s)
44 return EXIT_SUCCESS; // EOF (probably)
45 // valid s must be of form: SUBCMD | LEN | SP | FNAME
46 // N.B. we bail out on any error
47 // control or data file follows
48 if (2 == s[0] || 3 == s[0]) {
49 int fd;
50 size_t len;
51 // 2: control file (ignoring), 3: data file
52 fd = -1;
53 if (3 == s[0])
54 fd = xopen(queue, O_RDWR | O_APPEND);
55 // get data length
56 *strchrnul(s, ' ') = '\0';
57 len = xatou(s + 1);
58 // dump exactly len bytes to file, or die
59 bb_copyfd_exact_size(STDIN_FILENO, fd, len);
60 close(fd); // NB: can do close(-1). Who cares?
61 free(s);
62 // got no ACK? -> bail out
63 if (safe_read(STDIN_FILENO, s, 1) <= 0 || s[0]) {
64 // don't talk to peer - it obviously
65 // don't follow the protocol
66 return EXIT_FAILURE;
67 }
68 } else {
69 // any other subcommand aborts receiving job
70 // N.B. abort subcommand itself doesn't contain
71 // fname so it failed earlier...
72 break;
73 }
74 }
75 }
76
77 printf("Command %02x not supported\n", (unsigned char)*s);
78 return EXIT_FAILURE;
79}