示例#1
0
文件: print.c 项目: nysan/alpine
/*----------------------------------------------------------------------
       Open the printer

  Args: desc -- Description of item to print. Should have one trailing blank.

  Return value: < 0 is a failure.
		0 a success.

This does most of the work of popen so we can save the standard output of the
command we execute and send it back to the user.
  ----*/
int
open_printer(char *desc)
{
#ifndef _WINDOWS
    char command[201], prompt[200];
    int  cmd, rc, just_one;
    char *p, *init, *nick;
    char aname[100], wname[100];
    char *printer;
    int	 done = 0, i, lastprinter, cur_printer = 0;
    HelpType help;
    char   **list;
    static ESCKEY_S ekey[] = {
	/* TRANSLATORS: these are command labels for printing screen */
	{'y', 'y', "Y", N_("Yes")},
	{'n', 'n', "N", N_("No")},
	/* TRANSLATORS: go to Previous Printer in list */
	{ctrl('P'), 10, "^P", N_("Prev Printer")},
	{ctrl('N'), 11, "^N", N_("Next Printer")},
	{-2,   0,   NULL, NULL},
	/* TRANSLATORS: use Custom Print command */
	{'c', 'c', "C", N_("CustomPrint")},
	{KEY_UP,    10, "", ""},
	{KEY_DOWN,  11, "", ""},
	{-1, 0, NULL, NULL}};
#define PREV_KEY   2
#define NEXT_KEY   3
#define CUSTOM_KEY 5
#define UP_KEY     6
#define DOWN_KEY   7

    trailer      = NULL;
    init         = NULL;
    nick         = NULL;
    command[sizeof(command)-1] = '\0';

    if(ps_global->VAR_PRINTER == NULL){
        q_status_message(SM_ORDER | SM_DING, 3, 5,
	"No printer has been chosen.  Use SETUP on main menu to make choice.");
	return(-1);
    }

    /* Is there just one print command available? */
    just_one = (ps_global->printer_category!=3&&ps_global->printer_category!=2)
	       || (ps_global->printer_category == 2
		   && !(ps_global->VAR_STANDARD_PRINTER
			&& ps_global->VAR_STANDARD_PRINTER[0]
			&& ps_global->VAR_STANDARD_PRINTER[1]))
	       || (ps_global->printer_category == 3
		   && !(ps_global->VAR_PERSONAL_PRINT_COMMAND
			&& ps_global->VAR_PERSONAL_PRINT_COMMAND[0]
			&& ps_global->VAR_PERSONAL_PRINT_COMMAND[1]));

    if(F_ON(F_CUSTOM_PRINT, ps_global))
      ekey[CUSTOM_KEY].ch = 'c'; /* turn this key on */
    else
      ekey[CUSTOM_KEY].ch = -2;  /* turn this key off */

    if(just_one){
	ekey[PREV_KEY].ch = -2;  /* turn these keys off */
	ekey[NEXT_KEY].ch = -2;
	ekey[UP_KEY].ch   = -2;
	ekey[DOWN_KEY].ch = -2;
    }
    else{
	ekey[PREV_KEY].ch = ctrl('P'); /* turn these keys on */
	ekey[NEXT_KEY].ch = ctrl('N');
	ekey[UP_KEY].ch   = KEY_UP;
	ekey[DOWN_KEY].ch = KEY_DOWN;
	/*
	 * count how many printers in list and find the default in the list
	 */
	if(ps_global->printer_category == 2)
	  list = ps_global->VAR_STANDARD_PRINTER;
	else
	  list = ps_global->VAR_PERSONAL_PRINT_COMMAND;

	for(i = 0; list[i]; i++)
	  if(strcmp(ps_global->VAR_PRINTER, list[i]) == 0)
	    cur_printer = i;
	
	lastprinter = i - 1;
    }

    help = NO_HELP;
    ps_global->mangled_footer = 1;

    while(!done){
	if(init)
	  fs_give((void **)&init);

	if(trailer)
	  fs_give((void **)&trailer);

	if(just_one)
	  printer = ps_global->VAR_PRINTER;
	else
	  printer = list[cur_printer];

	parse_printer(printer, &nick, &p, &init, &trailer, NULL, NULL);
	strncpy(command, p, sizeof(command)-1);
	command[sizeof(command)-1] = '\0';
	fs_give((void **)&p);
	/* TRANSLATORS: Print something1 using something2.
	   For example, Print configuration using printer three. */
	snprintf(prompt, sizeof(prompt), _("Print %s using \"%s\" ? "),
		desc ? desc : "",
		*nick ? nick : command);
	prompt[sizeof(prompt)-1] = '\0';

	fs_give((void **)&nick);
	
	cmd = radio_buttons(prompt, -FOOTER_ROWS(ps_global),
				 ekey, 'y', 'x', help, RB_NORM);
	
	switch(cmd){
	  case 'y':
	    q_status_message1(SM_ORDER, 0, 9,
		"Printing with command \"%s\"", command);
	    done++;
	    break;

	  case 10:
	    cur_printer = (cur_printer>0)
				? (cur_printer-1)
				: lastprinter;
	    break;

	  case 11:
	    cur_printer = (cur_printer<lastprinter)
				? (cur_printer+1)
				: 0;
	    break;

	  case 'n':
	  case 'x':
	    done++;
	    break;

	  case 'c':
	    done++;
	    break;

	  default:
	    break;
	}
    }

    if(cmd == 'c'){
	if(init)
	  fs_give((void **)&init);

	if(trailer)
	  fs_give((void **)&trailer);

	snprintf(prompt, sizeof(prompt), "Enter custom command : ");
	prompt[sizeof(prompt)-1] = '\0';
	command[0] = '\0';
	rc = 1;
	help = NO_HELP;
	while(rc){
	    int flags = OE_APPEND_CURRENT;

	    rc = optionally_enter(command, -FOOTER_ROWS(ps_global), 0,
		sizeof(command), prompt, NULL, help, &flags);
	    
	    if(rc == 1){
		cmd = 'x';
		rc = 0;
	    }
	    else if(rc == 3)
	      help = (help == NO_HELP) ? h_custom_print : NO_HELP;
	    else if(rc == 0){
		removing_trailing_white_space(command);
		removing_leading_white_space(command);
		q_status_message1(SM_ORDER, 0, 9,
		    "Printing with command \"%s\"", command);
	    }
	}
    }

    if(cmd == 'x' || cmd == 'n'){
	q_status_message(SM_ORDER, 0, 2, "Print cancelled");
	if(init)
	  fs_give((void **)&init);

	if(trailer)
	  fs_give((void **)&trailer);

	return(-1);
    }

    display_message('x');

    ps_global->print = (PRINT_S *)fs_get(sizeof(PRINT_S));
    memset(ps_global->print, 0, sizeof(PRINT_S));

    strncpy(aname, ANSI_PRINTER, sizeof(aname)-1);
    aname[sizeof(aname)-1] = '\0';
    strncat(aname, "-no-formfeed", sizeof(aname)-strlen(aname)-1);
    strncpy(wname, WYSE_PRINTER, sizeof(wname)-1);
    wname[sizeof(wname)-1] = '\0';
    strncat(wname, "-no-formfeed", sizeof(wname)-strlen(wname)-1);
    if(strucmp(command, ANSI_PRINTER) == 0
       || strucmp(command, aname) == 0
       || strucmp(command, WYSE_PRINTER) == 0
       || strucmp(command, wname) == 0){
        /*----------- Attached printer ---------*/
        q_status_message(SM_ORDER, 0, 9,
	    "Printing to attached desktop printer...");
        display_message('x');
	xonxoff_proc(1);			/* make sure XON/XOFF used */
	crlf_proc(1);				/* AND LF->CR xlation */
	if(strucmp(command, ANSI_PRINTER) == 0
	   || strucmp(command, aname) == 0){
	    fputs("\033[5i", stdout);
	    ansi_off = 1;
	}
	else{
	    ansi_off = 0;
	    printf("%c", 18); /* aux on for wyse60,
			         Chuck Everett <*****@*****.**> */
	}

        ps_global->print->fp = stdout;
        if(strucmp(command, ANSI_PRINTER) == 0
	   || strucmp(command, WYSE_PRINTER) == 0){
	    /* put formfeed at the end of the trailer string */
	    if(trailer){
		int len = strlen(trailer);

		fs_resize((void **)&trailer, len+2);
		trailer[len] = '\f';
		trailer[len+1] = '\0';
	    }
	    else
	      trailer = cpystr("\f");
	}
    }
    else{
        /*----------- Print by forking off a UNIX command ------------*/
        dprint((4, "Printing using command \"%s\"\n",
	       command ? command : "?"));
	ps_global->print->result = temp_nam(NULL, "pine_prt");
	if(ps_global->print->result &&
	   (ps_global->print->pipe = open_system_pipe(command,
						      &ps_global->print->result, NULL,
						      PIPE_WRITE | PIPE_STDERR, 0,
						      pipe_callback, NULL))){
	    ps_global->print->fp = ps_global->print->pipe->out.f;
	}
	else{
	    if(ps_global->print->result){
		our_unlink(ps_global->print->result);
		fs_give((void **)&ps_global->print->result);
	    }

            q_status_message1(SM_ORDER | SM_DING, 3, 4,
			      "Error opening printer: %s",
                              error_description(errno));
            dprint((2, "Error popening printer \"%s\"\n",
                      error_description(errno)));
	    if(init)
	      fs_give((void **)&init);

	    if(trailer)
	      fs_give((void **)&trailer);
	    
	    return(-1);
        }
    }

    ps_global->print->err = 0;
    if(init){
	if(*init)
	  fputs(init, ps_global->print->fp);

	fs_give((void **)&init);
    }

    cb.cbuf[0] = '\0';
    cb.cbufp   = cb.cbuf;
    cb.cbufend = cb.cbuf;
#else /* _WINDOWS */
    int status;
    LPTSTR desclpt = NULL;

    if(desc)
      desclpt = utf8_to_lptstr(desc);

    if (status = mswin_print_ready (0, desclpt)) {
        q_status_message1(SM_ORDER | SM_DING, 3, 4,
			  "Error starting print job: %s",
			  mswin_print_error(status));
	if(desclpt)
	  fs_give((void **) &desclpt);

        return(-1);
    }

    if(desclpt)
      fs_give((void **) &desclpt);

    q_status_message(SM_ORDER, 0, 9, "Printing to windows printer...");
    display_message('x');

    /* init print control structure */
    ps_global->print = (PRINT_S *)fs_get(sizeof(PRINT_S));
    memset(ps_global->print, 0, sizeof(PRINT_S));

    ps_global->print->err = 0;
#endif /* _WINDOWS */

    return(0);
}
示例#2
0
/*
 * Break up the ldap-server string stored in the pinerc into its
 * parts. The structure is allocated here and should be freed by the caller.
 *
 * The original string looks like
 *     <servername>[:port] <SPACE> "/base=<base>/impl=1/..."
 *
 * Args  serv_str -- The original string from the pinerc to parse.
 *
 * Returns A pointer to a structure with filled in answers.
 *
 *  Some of the members have defaults. If port is -1, that means to use
 *  the default LDAP_PORT. If base is NULL, use "". Type and srch have
 *  defaults defined in alpine.h. If cust is non-NULL, it overrides type and
 *  srch.
 */
LDAP_SERV_S *
break_up_ldap_server(char *serv_str)
{
    char *lserv;
    char *q, *p, *tail;
    int   i, only_one = 1;
    LDAP_SERV_S *info = NULL;

    if(!serv_str)
      return(info);

    info = (LDAP_SERV_S *)fs_get(sizeof(LDAP_SERV_S));

    /*
     * Initialize to defaults.
     */
    memset((void *)info, 0, sizeof(*info));
    info->port  = -1;
    info->srch  = -1;
    info->type  = -1;
    info->time  = -1;
    info->size  = -1;
    info->scope = -1;

    /* copy the whole string to work on */
    lserv = cpystr(serv_str);
    if(lserv)
      removing_trailing_white_space(lserv);

    if(!lserv || !*lserv || *lserv == '"'){
	if(lserv)
	  fs_give((void **)&lserv);

	if(info)
	  free_ldap_server_info(&info);

	return(NULL);
    }

    tail = lserv;
    while((tail = strindex(tail, SPACE)) != NULL){
	tail++;
	if(*tail == '"' || *tail == '/'){
	    *(tail-1) = '\0';
	    break;
	}
	else
	  only_one = 0;
    }

    /* tail is the part after server[:port] <SPACE> */
    if(tail && *tail){
	removing_leading_white_space(tail);
	(void)removing_double_quotes(tail);
    }

    /* get the optional port number */
    if(only_one && (q = strindex(lserv, ':')) != NULL){
	int ldapport = -1;

	*q = '\0';
	if((ldapport = atoi(q+1)) >= 0)
	  info->port = ldapport;
    }

    /* use lserv for serv even though it has a few extra bytes alloced */
    info->serv = lserv;
    
    if(tail && *tail){
	/* get the search base */
	if((q = srchstr(tail, "/base=")) != NULL)
	  info->base = remove_backslash_escapes(q+6);

	if((q = srchstr(tail, "/binddn=")) != NULL)
	  info->binddn = remove_backslash_escapes(q+8);

	/* get the implicit parameter */
	if((q = srchstr(tail, "/impl=1")) != NULL)
	  info->impl = 1;

	/* get the rhs parameter */
	if((q = srchstr(tail, "/rhs=1")) != NULL)
	  info->rhs = 1;

	/* get the ref parameter */
	if((q = srchstr(tail, "/ref=1")) != NULL)
	  info->ref = 1;

	/* get the nosub parameter */
	if((q = srchstr(tail, "/nosub=1")) != NULL)
	  info->nosub = 1;

	/* get the tls parameter */
	if((q = srchstr(tail, "/tls=1")) != NULL)
	  info->tls = 1;

	/* get the tlsmust parameter */
	if((q = srchstr(tail, "/tlsm=1")) != NULL)
	  info->tlsmust = 1;

	/* get the search type value */
	if((q = srchstr(tail, "/type=")) != NULL){
	    NAMEVAL_S *v;

	    q += 6;
	    if((p = strindex(q, '/')) != NULL)
	      *p = '\0';
	    
	    for(i = 0; (v = ldap_search_types(i)); i++)
	      if(!strucmp(q, v->name)){
		  info->type = v->value;
		  break;
	      }
	    
	    if(p)
	      *p = '/';
	}

	/* get the search rule value */
	if((q = srchstr(tail, "/srch=")) != NULL){
	    NAMEVAL_S *v;

	    q += 6;
	    if((p = strindex(q, '/')) != NULL)
	      *p = '\0';
	    
	    for(i = 0; (v = ldap_search_rules(i)); i++)
	      if(!strucmp(q, v->name)){
		  info->srch = v->value;
		  break;
	      }
	    
	    if(p)
	      *p = '/';
	}

	/* get the scope */
	if((q = srchstr(tail, "/scope=")) != NULL){
	    NAMEVAL_S *v;

	    q += 7;
	    if((p = strindex(q, '/')) != NULL)
	      *p = '\0';
	    
	    for(i = 0; (v = ldap_search_scope(i)); i++)
	      if(!strucmp(q, v->name)){
		  info->scope = v->value;
		  break;
	      }
	    
	    if(p)
	      *p = '/';
	}

	/* get the time limit */
	if((q = srchstr(tail, "/time=")) != NULL){
	    q += 6;
	    if((p = strindex(q, '/')) != NULL)
	      *p = '\0';
	    
	    /* This one's a number */
	    if(*q){
		char *err;

		err = strtoval(q, &i, 0, 500, 0, tmp_20k_buf, SIZEOF_20KBUF, "ldap timelimit");
		if(err){
		  dprint((1, "%s\n", err ? err : "?"));
		}
		else
		  info->time = i;
	    }

	    if(p)
	      *p = '/';
	}

	/* get the size limit */
	if((q = srchstr(tail, "/size=")) != NULL){
	    q += 6;
	    if((p = strindex(q, '/')) != NULL)
	      *p = '\0';
	    
	    /* This one's a number */
	    if(*q){
		char *err;

		err = strtoval(q, &i, 0, 500, 0, tmp_20k_buf, SIZEOF_20KBUF, "ldap sizelimit");
		if(err){
		  dprint((1, "%s\n", err ? err : "?"));
		}
		else
		  info->size = i;
	    }

	    if(p)
	      *p = '/';
	}

	/* get the custom search filter */
	if((q = srchstr(tail, "/cust=")) != NULL)
	  info->cust = remove_backslash_escapes(q+6);

	/* get the nickname */
	if((q = srchstr(tail, "/nick=")) != NULL)
	  info->nick = remove_backslash_escapes(q+6);

	/* get the mail attribute name */
	if((q = srchstr(tail, "/matr=")) != NULL)
	  info->mailattr = remove_backslash_escapes(q+6);

	/* get the sn attribute name */
	if((q = srchstr(tail, "/satr=")) != NULL)
	  info->snattr = remove_backslash_escapes(q+6);

	/* get the gn attribute name */
	if((q = srchstr(tail, "/gatr=")) != NULL)
	  info->gnattr = remove_backslash_escapes(q+6);

	/* get the cn attribute name */
	if((q = srchstr(tail, "/catr=")) != NULL)
	  info->cnattr = remove_backslash_escapes(q+6);

	/* get the backup mail address */
	if((q = srchstr(tail, "/mail=")) != NULL)
	  info->mail = remove_backslash_escapes(q+6);
    }

    return(info);
}