source: MondoRescue/trunk/mondo/mondo/common/libmondo-fifo.c@ 42

Last change on this file since 42 was 42, checked in by bcornec, 19 years ago

asprintf usage continues on libmondo-fifo.c + indent

  • Property svn:keywords set to Id
File size: 4.6 KB
RevLine 
[42]1/* $Id: libmondo-fifo.c 42 2005-10-03 23:32:14Z bcornec $ */
[1]2
3/**
4 * @file
5 * Functions to handle buffering of tape archives as they are read/written.
6 * This used the external program @c buffer mostly.
7 */
8
9#include <unistd.h>
10#include <stdio.h>
11#include <signal.h>
[42]12#include <fcntl.h>
[1]13#include <stdio.h>
[42]14
[1]15#include <errno.h>
16#include <sys/types.h>
17#include <sys/stat.h>
18#include <sys/ipc.h>
19#include <sys/shm.h>
20#include <sys/sem.h>
21#include <sys/wait.h>
22#include <pthread.h>
23
24#include "my-stuff.h"
25#include "mondostructures.h"
26#include "libmondo.h"
27
28/**
29 * @addtogroup globalGroup
30 * @{
31 */
32/**
33 * The SIGPIPE handler sets this to TRUE.
34 */
[42]35bool g_sigpipe = FALSE;
[1]36
37/**
38 * PID of the "main" process.
39 */
[42]40pid_t g_mastermind_pid = 0;
[1]41
42
43
44/**
45 * Command line with which @c buffer was invoked.
46 */
[42]47char *g_sz_call_to_buffer;
[1]48
49/**
50 * Size of the buffer used with @c buffer.
51 */
[42]52int g_tape_buffer_size_MB = 0;
[1]53
54/* @} - end of globalGroup */
55
56
57/**
58 * @addtogroup fifoGroup
59 * @{
60 */
61/**
62 * Open a pipe to/from @c buffer.
63 * If buffer does not work at all, we use `dd'.
64 * @param device The device to read from/write to.
65 * @param direction @c 'r' (reading) or @c 'w' (writing).
66 * @return A file pointer to/from the @c buffer process.
67 */
[42]68FILE *open_device_via_buffer(char *device, char direction,
69 long internal_tape_block_size)
[1]70{
[42]71 char *sz_dir;
72 char keych;
73 char *tmp;
74 FILE *fres;
75 int bufsize; // in megabytes
76 int res;
77 int wise_upper_limit;
78 int wise_lower_limit;
[1]79
[42]80 assert_string_is_neither_NULL_nor_zerolength(device);
81 assert(direction == 'w' || direction == 'r');
82 asprintf(&sz_dir, "%c", direction);
83 wise_upper_limit = (am_I_in_disaster_recovery_mode()? 8 : 32);
84 wise_lower_limit = 1; // wise_upper_limit/2 + 1;
85 paranoid_system("sync");
86 for (bufsize = wise_upper_limit, res = -1;
87 res != 0 && bufsize >= wise_lower_limit; bufsize--) {
88 asprintf(&tmp,
89 "dd if=/dev/zero bs=1024 count=16k 2> /dev/null | buffer -o /dev/null -s %ld -m %d%c",
90 internal_tape_block_size, bufsize, 'm');
91 res = run_program_and_log_output(tmp, 2);
92 paranoid_free(tmp);
93 }
94 if (!res) {
95 bufsize++;
96 asprintf(&tmp, "Negotiated max buffer of %d MB ", bufsize);
97 log_to_screen(tmp);
98 paranoid_free(tmp);
99 } else {
100 bufsize = 0;
101 res = 0;
102 log_to_screen
103 ("Cannot negotiate a buffer of ANY size. Using dd instead.");
104 }
105 if (direction == 'r') {
106 keych = 'i';
107 } else {
108 keych = 'o';
109 }
110 if (bufsize) {
111 asprintf(&g_sz_call_to_buffer,
112 "buffer -m %d%c -p%d -B -s%ld -%c %s 2>> %s", bufsize,
113 'm', (direction == 'r') ? 20 : 75,
114 internal_tape_block_size, keych, device, MONDO_LOGFILE);
115 } else {
116 asprintf(&g_sz_call_to_buffer, "dd bs=%ld %cf=%s",
117 internal_tape_block_size, keych, device);
118 }
119 log_msg(2, "Calling buffer --- command = '%s'", g_sz_call_to_buffer);
120 fres = popen(g_sz_call_to_buffer, sz_dir);
121 paranoid_free(sz_dir);
122 if (fres) {
123 log_msg(2, "Successfully opened ('%c') tape device %s", direction,
124 device);
125 } else {
126 log_msg(2, "Failed to open ('%c') tape device %s", direction,
127 device);
128 }
129 sleep(2);
130 asprintf(&tmp, "ps wwax | grep \"%s\"", g_sz_call_to_buffer);
131 if (run_program_and_log_output(tmp, 2)) {
132 log_msg(2, "Warning - I think I failed to open tape, actually.");
133 }
134 paranoid_free(tmp);
135 g_tape_buffer_size_MB = bufsize;
136 /* BERLIOS: usless ?
137 strcmp(tmp, g_sz_call_to_buffer);
138 tmp[30] = '\0';
139 */
140 asprintf(&tmp, "ps wwax | grep buffer | grep -v grep");
141 if (run_program_and_log_output(tmp, 1)) {
142 fres = NULL;
143 log_to_screen("Failed to open tape streamer. Buffer error.");
144 } else {
145 log_to_screen("Buffer successfully started.");
146 }
147 paranoid_free(tmp);
148 return (fres);
[1]149}
150
151
152/**
153 * Kill @c buffer processes.
154 */
155void kill_buffer()
156{
[42]157 char *tmp;
158 char *command;
[1]159
[42]160 paranoid_system("sync");
161 asprintf(&command,
162 "ps wwax | fgrep \"%s\" | fgrep -v grep | awk '{print $1;}' | grep -v PID | tr -s '\n' ' ' | awk '{ print $1; }'",
163 g_sz_call_to_buffer);
164 paranoid_free(g_sz_call_to_buffer);
165 log_msg(2, "kill_buffer() --- command = %s", command);
[1]166
[42]167 asprintf(&tmp, "%s",
168 call_program_and_get_last_line_of_output(command));
169 paranoid_free(command);
[1]170
[42]171 asprintf(&command, "kill %s", tmp);
172 log_msg(2, "kill_buffer() --- command = %s", command);
[1]173
[42]174 if (strlen(tmp) > 0) {
175 run_program_and_log_output(command, TRUE);
176 }
177 paranoid_free(command);
178 paranoid_free(tmp);
179}
[1]180
181
182/**
183 * Handler for SIGPIPE.
184 * @param sig The signal that occurred (hopefully SIGPIPE).
185 */
186void sigpipe_occurred(int sig)
187{
[42]188 g_sigpipe = TRUE;
[1]189}
190
191/* @} - end of fifoGroup */
192
[42]193/* BERLIOS: useless ?
[1]194int
195extract_config_file_from_ramdisk( struct s_bkpinfo *bkpinfo,
196 char *ramdisk_fname,
197 char *output_cfg_file,
198 char *output_mountlist_file);
[42]199*/
Note: See TracBrowser for help on using the repository browser.