5 miniexpect - A very simple expect library for C.
12 #include <miniexpect.h>
15 h = mexp_spawnl ("ssh", "ssh", "host");
16 switch (mexp_expect (h, regexps, ovector, ovecsize)) {
21 cc prog.c -o prog -lminiexpect -lpcre
25 Miniexpect is a very simple expect-like library for C. Expect is a
26 way to control an external program that wants to be run interactively.
28 Miniexpect has a saner interface than libexpect, and doesn't depend on
29 Tcl. It is also thread safe, const-correct and uses modern C
32 Miniexpect is a standalone library, except for a single dependency: it
33 requires the PCRE (Perl Compatible Regular Expressions) library from
34 L<http://www.pcre.org/>. The PCRE dependency is fundamental because
35 we want to offer the most powerful regular expression syntax to match
36 on, but more importantly because PCRE has a convenient way to detect
37 partial matches which made this library very simple to implement.
39 This manual page documents the API. Examples of how to use the API
40 can be found in the source directory.
44 Miniexpect lets you start up an external program, control it (by
45 sending commands to it), and close it down gracefully. Two things
46 make this different from other APIs like L<popen(3)> and L<system(3)>:
47 Firstly miniexpect creates a pseudoterminal (pty). Secondly
48 miniexpect lets you match the output of the program using regular
49 expressions. Both of these are handy for controlling interactive
50 programs that might (for example) ask for passwords, but you can use
51 miniexpect on just about any external program.
53 You can control multiple programs at the same time.
55 =head1 SPAWNING THE SUBPROCESS
57 There are two calls for creating a subprocess:
59 B<mexp_h *mexp_spawnl (const char *file, const char *arg, ...);>
61 This creates a subprocess running the external program C<file> (the
62 current C<$PATH> is searched unless you give an absolute path).
63 C<arg, ...> are the arguments to the program. Usually the first
64 argument should be the name of the program.
66 The return value is a handle (see next section).
68 If there was an error running the subprocess, C<NULL> is returned and
69 the error is available in C<errno>.
71 For example, to run an ssh subprocess you could do:
73 h = mexp_spawnl ("ssh", "ssh", "-l", "root", "host");
75 or to run a particular ssh binary:
77 h = mexp_spawnl ("/usr/local/bin/ssh", "ssh", "-l", "root", "host");
79 An alternative to C<mexp_spawnl> is:
81 B<mexp_h *mexp_spawnv (const char *file, char **argv);>
83 This is the same as C<mexp_spawnl> except that you pass the arguments
84 in a NULL-terminated array.
88 After spawning a subprocess, you get back a handle. There are various
89 fields in this handle which you can read or write:
95 C<fd> is the pty of the subprocess. You can read and write to this if
96 you want, although convenience functions are also provided (see
97 below). C<pid> is the process ID of the subprocess. You can send it
102 C<timeout> is the timeout in milliseconds (1/1000th of a second) used
103 by C<mexp_expect> (see below). You can set this before calling
104 C<mexp_expect> if you want. Setting it to -1 means no timeout. The
105 default setting is 60000 (60 seconds).
111 If C<mexp_expect> returns a match then these variables contain the
112 read buffer. Note this buffer does not contain the full input from
113 the process, but it will contain at least the part matched by the
114 regular expression (and maybe some more). C<buffer> is the read
115 buffer and C<len> is the number of bytes of data in the buffer.
119 If C<mexp_expect> returns a match, then C<next_match> points to the
120 first byte in the buffer I<after> the fully matched expression. (It
121 may be C<-1> which means it is invalid). The next time that
122 C<mexp_expect> is called, it will start by consuming the data
123 C<buffer[next_match...len-1]>. Callers may also need to read from
124 that point in the buffer before calling L<read(2)> on the file
125 descriptor. Callers may also set this, for example setting it to
126 C<-1> in order to ignore the remainder of the buffer. In most cases
127 callers can ignore this field, and C<mexp_expect> will just do the
128 right thing when called repeatedly.
132 Callers may set this to the natural size (in bytes) for reads from the
133 subprocess. The default is 1024. Most callers will not need to
138 If C<mexp_expect> returns C<MEXP_PCRE_ERROR>, then the actual PCRE
139 error code returned by L<pcre_exec(3)> is available here. For a list
140 of PCRE error codes, see L<pcreapi(3)>.
146 Opaque pointers for use by the caller. The library will not touch
151 typedef struct mexp_h mexp_h;
153 =head1 CLOSING THE HANDLE
155 To close the handle and clean up the subprocess, call:
157 B<int mexp_close (mexp_h *h);>
159 This returns the status code from the subprocess. This is in the form
160 of a L<waitpid(2)>/L<system(3)> status so you have to use the macros
161 C<WIFEXITED>, C<WEXITSTATUS>, C<WIFSIGNALED>, C<WTERMSIG> etc defined
162 in C<E<lt>sys/wait.hE<gt>> to parse it.
164 If there was a system call error, then C<-1> is returned. The error
173 Even in error cases, the handle is always closed and its memory is
178 It is normal for the kernel to send SIGHUP to the subprocess.
180 If the subprocess doesn't catch the SIGHUP, then it will die
183 WIFSIGNALED (status) && WTERMSIG (status) == SIGHUP
185 This case should not necessarily be considered an error.
189 This is how code should check for and print errors from C<mexp_close>:
191 status = mexp_close (h);
193 perror ("mexp_close");
196 if (WIFSIGNALED (status) && WTERMSIG (status) == SIGHUP)
197 goto ignore; /* not an error */
198 if (!WIFEXITED (status) || WEXITSTATUS (status) != 0)
199 /* You could use the W* macros to print a better error message. */
200 fprintf (stderr, "error: subprocess failed, status = %d", status);
206 =head1 EXPECT FUNCTION
208 Miniexpect contains a powerful regular expression matching function
211 B<int mexp_expect (mexp_h *h, const mexp_regexp *regexps,
212 int *ovector, int ovecsize);>
214 The output of the subprocess is matched against the list of PCRE
215 regular expressions in C<regexps>. C<regexps> is a list of regular
216 expression structures:
221 const pcre_extra *extra;
224 typedef struct mexp_regexp mexp_regexp;
226 C<r> is the integer code returned from C<mexp_expect> if this regular
227 expression matches. It B<must> be E<gt> 0. C<r == 0> indicates the
228 end of the list of regular expressions. C<re> is the compiled regular
231 Possible return values are:
235 =item C<MEXP_TIMEOUT>
237 No input matched before the timeout (C<h-E<gt>timeout>) was
242 The subprocess closed the connection.
246 There was a system call error (eg. from the read call). The error is
247 returned in C<errno>.
249 =item C<MEXP_PCRE_ERROR>
251 There was a C<pcre_exec> error. C<h-E<gt>pcre_error> is set to the
252 error code. See L<pcreapi(3)> for a list of the C<PCRE_*> error codes
257 If any regexp matches, the associated integer code (C<regexps[].r>)
268 C<regexps> may be NULL or an empty list, which means we don't match
269 against a regular expression. This is useful if you just want to wait
274 C<regexps[].re>, C<regexps[].extra>, C<regexps[].options>, C<ovector>
275 and C<ovecsize> are passed through to the L<pcre_exec(3)> function.
279 If multiple regular expressions are passed, then they are checked in
280 turn and the I<first> regular expression that matches is returned
281 I<even if the match happens later in the input than another regular
284 For example if the input is C<"hello world"> and you pass the two
287 regexps[0].re = world
288 regexps[1].re = hello
290 then the first regular expression (C<"world">) may match and the
291 C<"hello"> part of the input may be ignored.
293 In some cases this can even lead to unpredictable matching. In the
294 case above, if we only happened to read C<"hello wor">, then the
295 second regular expression (C<"hello">) I<would> match.
297 If this is a concern, combine your regular expressions into a single
298 one, eg. C<(hello)|(world)>.
302 =head2 mexp_expect example
304 It is easier to understand C<mexp_expect> by considering a simple
307 In this example we are waiting for ssh to either send us a password
308 prompt, or (if no password was required) a command prompt, and based
309 on the output we will either send back a password or a command.
311 The unusual C<(mexp_regexp[]){...}> syntax is called a "compound
312 literal" and is available in C99. If you need to use an older
313 compiler, you can just use a local variable instead.
318 pcre *password_re, *prompt_re;
319 const int ovecsize = 12;
320 int ovector[ovecsize];
322 password_re = pcre_compile ("assword", 0, &errptr, &offset, NULL);
323 prompt_re = pcre_compile ("[$#] ", 0, &errptr, &offset, NULL);
325 switch (mexp_expect (h,
327 { 100, .re = password_re },
328 { 101, .re = prompt_re },
330 }, ovector, ovecsize)) {
332 /* here you would send a password */
335 /* here you would send a command */
338 fprintf (stderr, "error: ssh closed the connection unexpectedly\n");
341 fprintf (stderr, "error: timeout before reaching the prompt\n");
344 perror ("mexp_expect");
346 case MEXP_PCRE_ERROR:
347 fprintf (stderr, "error: PCRE error: %d\n", h->pcre_error);
351 =head1 SENDING COMMANDS TO THE SUBPROCESS
353 You can write to the subprocess simply by writing to C<h-E<gt>fd>.
354 However we also provide a convenience function:
356 B<int mexp_printf (mexp_h *h, const char *fs, ...);>
358 This returns the number of bytes, if the whole message was written OK.
359 If there was an error, -1 is returned and the error is available in
368 C<mexp_printf> will not do a partial write. If it cannot write all
369 the data, then it will return an error.
373 This function does not write a newline automatically. If you want to
374 send a command followed by a newline you have to do something like:
376 mexp_printf (h, "exit\n");
382 Source is available from:
383 L<http://git.annexia.org/?p=miniexpect.git;a=summary>
395 Richard W.M. Jones (C<rjones at redhat dot com>)
399 The library is released under the Library GPL (LGPL) version 2 or at
400 your option any later version.
404 Copyright (C) 2014 Red Hat Inc.