Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ImplicitClasses has no effect during failover #2766

Closed
michaelrsweet opened this issue Mar 20, 2008 · 9 comments
Closed

ImplicitClasses has no effect during failover #2766

michaelrsweet opened this issue Mar 20, 2008 · 9 comments
Milestone

Comments

@michaelrsweet
Copy link
Collaborator

Version: 1.3.5
CUPS.org User: relovett

I setup two CUPS servers with the intent of one being the backup of the other. With a Mac OS X 10.5.2 client configured with:

BrowseShortNames Yes
ImplicitClasses Yes
ImplicitAnyClasses No
HideImplicitMembers Yes

it is able to browse the full printer queues on each and merge the queue names into the implicit class name as expected. lpstat lists the queues as q1, q2, etc. When I turned off cupsd on the primary CUPS server to test failover however, the implicit queue names disappeared on the client and I am left with 'q1@backup', 'q2@backup', etc. as queue names.

When I tried removing remote.cache and running 'launchctl stop org.cups.cupsd' but that did not change the behavior.

@michaelrsweet
Copy link
Collaborator Author

CUPS.org User: krumboeck

This bug is not specific to an operating system. We have the same problem on HP-UX with CUPS 1.3.x (never had this problem with 1.2.x).

Sadly we had too less time and informations for further analyses.

What we have seen so far:
*) Sometimes it help to stop cups, delete remote.cache file and start cups
*) When the first workaround doesn't help, then you can install remote.cache file from a working client. This seems to solve the problem for a longer time.
*) It happens at least since 1.3.2 (we didn't install earlier versions on our production hosts)
*) This problem doesn't exist in 1.2.11 and earlier versions.
*) Maybe it has to do with CUPS server crashes or restarts, but this is not confirmed.

Our client machines:
HP-UX 11.31 (ia64) CUPS 1.3.6
HP-UX 11.23 (ia64) CUPS 1.3.6
HP-UX 11.11 (hppa) CUPS 1.3.6

CUPS version is tar.gz from www.cups.org.

I will post the configuration file and remote.cache file from an affected machine.

regards!
Bernd

@michaelrsweet
Copy link
Collaborator Author

CUPS.org User: krumboeck

remote.cache.sk ... remote cache file from another HP-UX CUPS client, which had also problems with ImplicitClasses.

The results are very similar to the above one, but in this case the implicit class exists. Sadly there also exists remote queues, which shouldn't be possible.

The config is exact the same like the other host.

@michaelrsweet
Copy link
Collaborator Author

CUPS.org User: mike

Not sure what is going wrong here, but looking into it...

@michaelrsweet
Copy link
Collaborator Author

CUPS.org User: mike

OK, I think the problem is the timing out is removing the original queue (which won't delete the implicit class), but when we re-discover the queue it replaces the implicit class with the remote printer. Finally, remote.cache is saved with the short name, and you are stuck with no implicit classes from then on...

A workaround for now is to add the following to your cupsd.conf file:

BrowseShortNames No

You can use the cupsctl command for this:

cupsctl BrowseShortNames=No

@michaelrsweet
Copy link
Collaborator Author

CUPS.org User: mike

Fixed in Subversion repository.

@michaelrsweet
Copy link
Collaborator Author

CUPS.org User: mike

and the patch against 1.3.x...

@michaelrsweet
Copy link
Collaborator Author

"cupsd.conf":

"$Id: cupsd.conf.in 5454 2006-04-23 21:46:38Z mike $"

Sample configuration file for the Common UNIX Printing System (CUPS)

scheduler. See "man cupsd.conf" for a complete description of this

file.

Log general information in error_log - change "info" to "debug" for

troubleshooting...

LogLevel info

Administrator user group...

SystemGroup sys root

Only listen for connections from the local machine.

Listen localhost:631

Listen *:631
Listen /var/run/cups/cups.sock

Show shared printers on the local network.

Browsing On
BrowseOrder allow,deny

BrowseAllow @Local

BrowseInterval 1200
BrowseTimeout 14400

BrowseProtocols cups
BrowsePoll 192.164.184.16:631
BrowsePoll 192.164.184.17:631

Default authentication type, when authentication is required...

DefaultAuthType Basic

Restrict access to the server...

Order allow,deny Allow All

Restrict access to the admin pages...

<Location /admin>
AuthType BasicDigest
Encryption Required
Require user @System
Order allow,deny
Allow All

Restrict access to configuration files...

<Location /admin/conf>
AuthType BasicDigest
Require user @System
Order allow,deny
Allow All

Set the default printer/job policies...

# Job-related operations must be done by the owner or an adminstrator... Require user @owner @System Order deny,allow

All administration operations require an adminstrator to authenticate...

AuthType Basic Require user @System Order deny,allow

Only the owner or an administrator can cancel or authenticate a job...

Require user @owner @System Order deny,allow Order deny,allow

End of "$Id: cupsd.conf.in 5454 2006-04-23 21:46:38Z mike $".

@michaelrsweet
Copy link
Collaborator Author

"str2766.patch":

Index: scheduler/dirsvc.c

--- scheduler/dirsvc.c (revision 7722)
+++ scheduler/dirsvc.c (working copy)
@@ -802,7 +802,7 @@
to; /* Timeout time */

  • if (!Browsing || !BrowseLocalProtocols || !Printers)
  • if (!Browsing || !Printers)
    return;

/*
@@ -816,7 +816,7 @@

  • Figure out how many printers need an update...
    */
  • if (BrowseInterval > 0)
  • if (BrowseInterval > 0 && BrowseLocalProtocols)
    {
    int max_count; /* Maximum number to update */

@@ -894,7 +894,7 @@
}

/*

  • * Loop through all of the printers and send local updates as needed...

    • Loop through all of the printers and timeout old printers as needed...
      */

    for (p = (cupsd_printer_t *)cupsArrayFirst(Printers);
    @@ -905,25 +905,24 @@

    • If this is a remote queue, see if it needs to be timed out...
      */
  • if (p->type & CUPS_PRINTER_DISCOVERED)

  • if ((p->type & CUPS_PRINTER_DISCOVERED) &&

  •    !(p->type & CUPS_PRINTER_IMPLICIT) &&
    
  • p->browse_expire < to)
    {

  •  if (p->browse_expire < to)
    
  •  {
    
  • cupsdAddEvent(CUPSD_EVENT_PRINTER_DELETED, p, NULL,

  •                  "%s \'%s\' deleted by directory services (timeout).",
    
  •         (p->type & CUPS_PRINTER_CLASS) ? "Class" : "Printer",
    
  •  cupsdAddEvent(CUPSD_EVENT_PRINTER_DELETED, p, NULL,
    
  •       "%s \'%s\' deleted by directory services (timeout).",
    
  •       (p->type & CUPS_PRINTER_CLASS) ? "Class" : "Printer",
    
  •       p->name);
    
  •  cupsdLogMessage(CUPSD_LOG_DEBUG,
    
  •         "Remote destination \"%s\" has timed out; "
    
  •         "deleting it...",
          p->name);
    
  •    cupsdLogMessage(CUPSD_LOG_DEBUG,
    
  •               "Remote destination \"%s\" has timed out; "
    
  •       "deleting it...",
    

- p->name);

  •    cupsArraySave(Printers);
    
  •    cupsdDeletePrinter(p, 1);
    
  •    cupsArrayRestore(Printers);
    
  •    cupsdMarkDirty(CUPSD_DIRTY_PRINTCAP | CUPSD_DIRTY_REMOTE);
    
  •  }
    
  •  cupsArraySave(Printers);
    
  •  cupsdDeletePrinter(p, 1);
    
  •  cupsArrayRestore(Printers);
    
  •  cupsdMarkDirty(CUPSD_DIRTY_PRINTCAP | CUPSD_DIRTY_REMOTE);
    
    }
    }
    }
    @@ -2439,13 +2438,23 @@
    newname[IPP_MAX_NAME], /* New name of printer /
    *hptr, /
    Pointer into hostname /
    *sptr; /
    Pointer into ServerName */
  • const char shortname; / Short queue name (queue) /
    char local_make_model[IPP_MAX_NAME];
    /
    Local make and model /
    cupsd_printer_t *p; /
    Printer information /
    const char *ipp_options, /
    ipp-options value /
    *lease_duration; /
    lease-duration value */
  • int is_class; /* Is this queue a class? */
  • cupsdLogMessage(CUPSD_LOG_DEBUG2,
  •              "process_browse_data(uri=\"%s\", host=\"%s\", "
    
  •     "resource=\"%s\", type=%x, state=%d, location=\"%s\", "
    
  •     "info=\"%s\", make_model=\"%s\", num_attrs=%d, attrs=%p)",
    
  •     uri, host, resource, type, state,
    
  •     location ? location : "(nil)", info ? info : "(nil)",
    
  •     make_model ? make_model : "(nil)", num_attrs, attrs);
    
    /*
    • Determine if the URI contains any illegal characters in it...
      */
      @@ -2454,9 +2463,7 @@
      (strncmp(resource, "/printers/", 10) &&
      strncmp(resource, "/classes/", 9)))
      {
  • cupsdLogMessage(CUPSD_LOG_ERROR,
  •                "process_browse_data: Bad printer URI in browse data: %s",
    
  •                uri);
    
  • cupsdLogMessage(CUPSD_LOG_ERROR, "Bad printer URI in browse data: %s", uri);
    return;
    }

@@ -2464,8 +2471,7 @@
(!strncmp(resource, "/printers/", 10) && strchr(resource + 10, '/')) ||
(!strncmp(resource, "/classes/", 9) && strchr(resource + 9, '/')))
{

  • cupsdLogMessage(CUPSD_LOG_ERROR,
  •                "process_browse_data: Bad resource in browse data: %s",
    
  • cupsdLogMessage(CUPSD_LOG_ERROR, "Bad resource in browse data: %s",
    resource);
    return;
    }
    @@ -2520,11 +2526,12 @@
  • See if we already have it listed in the Printers list, and add it if not...
    */
  • type |= CUPS_PRINTER_REMOTE | CUPS_PRINTER_DISCOVERED;
  • type &= ~CUPS_PRINTER_IMPLICIT;
  • update = 0;
  • hptr = strchr(host, '.');
  • sptr = strchr(ServerName, '.');
  • type |= CUPS_PRINTER_REMOTE | CUPS_PRINTER_DISCOVERED;
  • type &= ~CUPS_PRINTER_IMPLICIT;
  • update = 0;
  • hptr = strchr(host, '.');
  • sptr = strchr(ServerName, '.');
  • is_class = type & CUPS_PRINTER_CLASS;

if (!ServerNameIsIP && sptr != NULL && hptr != NULL)
{
@@ -2544,7 +2551,7 @@
}
}

  • if (type & CUPS_PRINTER_CLASS)
  • if (is_class)
    {
    /*
  • Remote destination is a class...
    @@ -2555,210 +2562,140 @@
    else
    return;
  • if (hptr && !*hptr)
  •  _hptr = '.';         /_ Resource FQDN */
    
  • shortname = resource + 9;
  • }
  • else
  • {
  • /*
  • * Remote destination is a printer...
  • */
  • if ((p = cupsdFindDest(name)) == NULL && BrowseShortNames)
  • {
  •  if ((p = cupsdFindDest(resource + 9)) != NULL)
    
  •  {
    
  •    if (p->hostname && strcasecmp(p->hostname, host))
    
  • {
  • /*
  • \* Nope, this isn't the same host; if the hostname isn't the local host,
    
  • \* add it to the other class and then find a class using the full host
    
  • \* name...
    
  • */
    
  • if (!strncmp(resource, "/printers/", 10))
  •  snprintf(name, sizeof(name), "%s@%s", resource + 10, host);
    
  • else
  •  return;
    
  • if (p->type & CUPS_PRINTER_REMOTE)
    
  • {
    
  •   cupsdLogMessage(CUPSD_LOG_DEBUG,
    
  •                   "Renamed remote class \"%s\" to \"%s@%s\"...",
    
  •                   p->name, p->name, p->hostname);
    
  •   cupsdAddEvent(CUPSD_EVENT_PRINTER_DELETED, p, NULL,
    
  •                 "Class \'%s\' deleted by directory services.",
    
  •         p->name);
    
  • shortname = resource + 10;
  • }
  •        snprintf(newname, sizeof(newname), "%s@%s", p->name, p->hostname);
    
  •        cupsdRenamePrinter(p, newname);
    
  • if (hptr && !*hptr)
  • hptr = '.'; / Resource FQDN */
  •   cupsdAddEvent(CUPSD_EVENT_PRINTER_ADDED, p, NULL,
    
  •                 "Class \'%s\' added by directory services.",
    
  •         p->name);
    
  • }
    
  • if ((p = cupsdFindDest(name)) == NULL && BrowseShortNames)
  • {
  • /*
  • * Long name doesn't exist, try short name...
  • */
  •      p = NULL;
    
  • }
  • else if (!p->hostname)
  • {
  • /*
  • \* Hostname not set, so this must be a cached remote printer
    
  • \* that was created for a pending print job...
    
  • */
    
  • cupsdLogMessage(CUPSD_LOG_DEBUG, "process_browse_data: %s not found...",
  •                name);
    
  •      cupsdSetString(&p->hostname, host);
    
  • cupsdSetString(&p->uri, uri);
    
  • cupsdSetString(&p->device_uri, uri);
    
  •      update = 1;
    
  •    }
    
  •  }
    
  •  else
    
  •  {
    
  •   /*
    
  •    \* Use the short name for this shared class.
    

- */

  •    strlcpy(name, resource + 9, sizeof(name));
    
  •  }
    
  • }

  • else if (p && !p->hostname)

  • if ((p = cupsdFindDest(shortname)) == NULL)
    {
    /*

  •  \* Hostname not set, so this must be a cached remote printer
    
  •  \* that was created for a pending print job...
    
  •  * Short name doesn't exist, use it for this shared queue.
    

    */

  •  cupsdSetString(&p->hostname, host);
    
  •  cupsdSetString(&p->uri, uri);
    
  •  cupsdSetString(&p->device_uri, uri);
    
  •  update = 1;
    
  •  cupsdLogMessage(CUPSD_LOG_DEBUG2, "process_browse_data: %s not found...",
    
  •         shortname);
    
  •  strlcpy(name, shortname, sizeof(name));
    

    }

  • if (!p)

  • else
    {
    /*

  •  \* Class doesn't exist; add it...
    
  •  * Short name exists...
    

    */

  •  p = cupsdAddClass(name);
    
  •  cupsdLogMessage(CUPSD_LOG_DEBUG2,
    
  •                  "process_browse_data: %s found, type=%x, hostname=%s...",
    
  •         shortname, p->type, p->hostname ? p->hostname : "(nil)");
    
  •  cupsdLogMessage(CUPSD_LOG_DEBUG, "Added remote class \"%s\"...", name);
    
  •  if (p->type & CUPS_PRINTER_IMPLICIT)
    
  •    p = NULL;          /\* Don't replace implicit classes */
    
  •  else if (p->hostname && strcasecmp(p->hostname, host))
    
  •  {
    
  •   /*
    
  • * Short name exists but is for a different host. If this is a remote

  • * queue, rename it and use the long name...

  • */

  •  cupsdAddEvent(CUPSD_EVENT_PRINTER_ADDED, p, NULL,
    
  •                "Class \'%s\' added by directory services.", name);
    
  • if (p->type & CUPS_PRINTER_REMOTE)

  • {

  • cupsdLogMessage(CUPSD_LOG_DEBUG,
    
  •         "Renamed remote %s \"%s\" to \"%s@%s\"...",
    
  •         is_class ? "class" : "printer", p->name, p->name,
    
  •         p->hostname);
    
  • cupsdAddEvent(CUPSD_EVENT_PRINTER_DELETED, p, NULL,
    
  •       "%s \'%s\' deleted by directory services.",
    
  •       is_class ? "Class" : "Printer", p->name);
    
  • /*
    
  •  \* Force the URI to point to the real server...
    
  •  */
    
  • snprintf(newname, sizeof(newname), "%s@%s", p->name, p->hostname);
    
  • cupsdRenamePrinter(p, newname);
    
  •  p->type      = type & ~CUPS_PRINTER_REJECTING;
    
  •  p->accepting = 1;
    
  •  cupsdSetString(&p->uri, uri);
    
  •  cupsdSetString(&p->device_uri, uri);
    
  •  cupsdSetString(&p->hostname, host);
    
  • cupsdAddEvent(CUPSD_EVENT_PRINTER_ADDED, p, NULL,
    
  •       "%s \'%s\' added by directory services.",
    
  •       is_class ? "Class" : "Printer", p->name);
    
  • }

  •  update = 1;
    
  •   /*
    
  •    \* Force creation with long name...
    
  • */

  •  cupsdMarkDirty(CUPSD_DIRTY_PRINTCAP | CUPSD_DIRTY_REMOTE);
    
  • p = NULL;

  •  }
    

    }
    }
    else

  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •       "process_browse_data: %s found, type=%x, hostname=%s...",
    
  •       name, p->type, p->hostname ? p->hostname : "(nil)");
    
  • if (!p)
    {
    /*

  • * Remote destination is a printer...

    • Queue doesn't exist; add it...
      */
  • if (!strncmp(resource, "/printers/", 10))

  •  snprintf(name, sizeof(name), "%s@%s", resource + 10, host);
    
  • if (is_class)

  •  p = cupsdAddClass(name);
    

    else

  •  return;
    
  •  p = cupsdAddPrinter(name);
    
  • if (hptr && !*hptr)

  •  _hptr = '.';         /_ Resource FQDN */
    
  • cupsdClearString(&(p->hostname));

  • if ((p = cupsdFindDest(name)) == NULL && BrowseShortNames)

  • {

  •  if ((p = cupsdFindDest(resource + 10)) != NULL)
    
  •  {
    
  •    if (p->hostname && strcasecmp(p->hostname, host))
    
  • {

  • /*

  • \* Nope, this isn't the same host; if the hostname isn't the local host,
    
  • \* add it to the other printer and then find a printer using the full host
    
  • \* name...
    
  • */
    
  • cupsdLogMessage(CUPSD_LOG_DEBUG, "Added remote %s "%s"...",

  •                is_class ? "class" : "printer", name);
    
  • if (p->type & CUPS_PRINTER_REMOTE)
    
  • {
    
  •   cupsdLogMessage(CUPSD_LOG_DEBUG,
    
  •                   "Renamed remote printer \"%s\" to \"%s@%s\"...",
    
  •                   p->name, p->name, p->hostname);
    
  •   cupsdAddEvent(CUPSD_EVENT_PRINTER_DELETED, p, NULL,
    
  •                 "Printer \'%s\' deleted by directory services.",
    
  •         p->name);
    
  • cupsdAddEvent(CUPSD_EVENT_PRINTER_ADDED, p, NULL,

  •     "%s \'%s\' added by directory services.",
    
  •     is_class ? "Class" : "Printer", name);
    
  •        snprintf(newname, sizeof(newname), "%s@%s", p->name, p->hostname);
    
  •        cupsdRenamePrinter(p, newname);
    
  • /*

  • * Force the URI to point to the real server...

  • */

  •   cupsdAddEvent(CUPSD_EVENT_PRINTER_ADDED, p, NULL,
    
  •                 "Printer \'%s\' added by directory services.",
    
  •         p->name);
    
  • }
    
  • p->type = type & ~CUPS_PRINTER_REJECTING;

  • p->accepting = 1;

  •      p = NULL;
    
  • }

  • else if (!p->hostname)

  • {

  • /*

  • \* Hostname not set, so this must be a cached remote printer
    
  • \* that was created for a pending print job...
    
  • */
    
  • cupsdMarkDirty(CUPSD_DIRTY_PRINTCAP);

  • }

  •      cupsdSetString(&p->hostname, host);
    
  • cupsdSetString(&p->uri, uri);
    
  • cupsdSetString(&p->device_uri, uri);
    
  •      update = 1;
    
  •    }
    
  •  }
    
  •  else
    
  •  {
    
  •   /*
    
  •    \* Use the short name for this shared printer.
    
  • */

  • if (!p)

  • return;

  •    strlcpy(name, resource + 10, sizeof(name));
    
  •  }
    
  • }

  • else if (p && !p->hostname)

  • {

  • /*
    
  •  \* Hostname not set, so this must be a cached remote printer
    
  •  \* that was created for a pending print job...
    
  •  */
    
  • if (!p->hostname)

  • {

  • /*

  • * Hostname not set, so this must be a cached remote printer

  • * that was created for a pending print job...

  • */

  •  cupsdSetString(&p->hostname, host);
    
  •  cupsdSetString(&p->uri, uri);
    
  •  cupsdSetString(&p->device_uri, uri);
    
  •  update = 1;
    
  • }

  • cupsdSetString(&p->hostname, host);

  • cupsdSetString(&p->uri, uri);

  • cupsdSetString(&p->device_uri, uri);

  • update = 1;

  • if (!p)

  • {

  • /*
    
  •  \* Printer doesn't exist; add it...
    

- */

- p = cupsdAddPrinter(name);

  •  cupsdAddEvent(CUPSD_EVENT_PRINTER_ADDED, p, NULL,
    

- "Printer '%s' added by directory services.", name);

- cupsdLogMessage(CUPSD_LOG_DEBUG, "Added remote printer "%s"...", name);

  • /*
    
  •  \* Force the URI to point to the real server...
    

- */

  •  p->type      = type & ~CUPS_PRINTER_REJECTING;
    
  •  p->accepting = 1;
    
  •  cupsdSetString(&p->hostname, host);
    
  •  cupsdSetString(&p->uri, uri);
    

- cupsdSetString(&p->device_uri, uri);

- update = 1;

  •  cupsdMarkDirty(CUPSD_DIRTY_PRINTCAP | CUPSD_DIRTY_REMOTE);
    
  • }
  • cupsdMarkDirty(CUPSD_DIRTY_REMOTE);
    }

/*
@@ -2823,7 +2760,7 @@

if (!make_model || !make_model[0])
{

  • if (type & CUPS_PRINTER_CLASS)

  • if (is_class)
    snprintf(local_make_model, sizeof(local_make_model),
    "Remote Class on %s", host);
    else
    @@ -2877,7 +2814,7 @@
    {
    cupsdAddEvent(CUPSD_EVENT_PRINTER_DELETED, p, NULL,
    "%s '%s' deleted by directory services.",

  •     (type & CUPS_PRINTER_CLASS) ? "Class" : "Printer", p->name);
    
  •     is_class ? "Class" : "Printer", p->name);
    

    cupsdExpireSubscriptions(p, NULL);

Index: scheduler/printers.c

--- scheduler/printers.c (revision 7723)
+++ scheduler/printers.c (working copy)
@@ -133,6 +133,8 @@
if (!Printers)
Printers = cupsArrayNew(compare_printers, NULL);

  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •              "cupsdAddPrinter: Adding %s to Printers", p->name);
    

    cupsArrayAdd(Printers, p);

    if (!ImplicitPrinters)
    @@ -640,10 +642,17 @@

    • Remove the printer from the list...
      */
  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •              "cupsdDeletePrinter: Removing %s from Printers", p->name);
    

    cupsArrayRemove(Printers, p);

    if (p->type & CUPS_PRINTER_IMPLICIT)

  • {

  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •       "cupsdDeletePrinter: Removing %s from ImplicitPrinters",
    
  •       p->name);
    

    cupsArrayRemove(ImplicitPrinters, p);

  • }

/*

  • Remove the dummy interface/icon/option files under IRIX...
    @@ -1285,10 +1294,17 @@

  • Remove the printer from the array(s) first...
    */

  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •              "cupsdRenamePrinter: Removing %s from Printers", p->name);
    

    cupsArrayRemove(Printers, p);

    if (p->type & CUPS_PRINTER_IMPLICIT)

  • {

  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •       "cupsdRenamePrinter: Removing %s from ImplicitPrinters",
    
  •       p->name);
    

    cupsArrayRemove(ImplicitPrinters, p);

  • }

/*

  • Rename the printer type...
    @@ -1316,10 +1332,17 @@

  • Add the printer back to the printer array(s)...
    */

  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •              "cupsdRenamePrinter: Adding %s to Printers", p->name);
    

    cupsArrayAdd(Printers, p);

    if (p->type & CUPS_PRINTER_IMPLICIT)

  • {

  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •       "cupsdRenamePrinter: Adding %s to ImplicitPrinters",
    
  •       p->name);
    

    cupsArrayAdd(ImplicitPrinters, p);

  • }
    }

Index: scheduler/main.c

--- scheduler/main.c (revision 7722)
+++ scheduler/main.c (working copy)
@@ -941,7 +941,7 @@
#endif /* HAVE_LDAP */
}

  • if (Browsing && BrowseLocalProtocols && current_time > browse_time)
  • if (Browsing && current_time > browse_time)
    {
    cupsdSendBrowseList();
    browse_time = current_time;
    Index: scheduler/classes.c
    ===================================================================
    --- scheduler/classes.c (revision 7722)
    +++ scheduler/classes.c (working copy)
    @@ -210,7 +210,8 @@
    c = (cupsd_printer_t *)cupsArrayNext(ImplicitPrinters))
    if (c->num_printers == 0)
    {
  •  cupsArrayRemove(ImplicitPrinters, c);
    
  •  cupsdLogMessage(CUPSD_LOG_DEBUG, "Deleting implicit class \"%s\"...",
    
  •                  c->name);
    
    cupsdDeletePrinter(c, 0);
    }
    }

@michaelrsweet
Copy link
Collaborator Author

"str2766-1.3.patch":

Index: scheduler/dirsvc.c

--- scheduler/dirsvc.c (revision 7724)
+++ scheduler/dirsvc.c (revision 7725)
@@ -793,7 +793,7 @@
int write_printcap; /* Write the printcap file? */

  • if (!Browsing || !BrowseLocalProtocols || !Printers)
  • if (!Browsing || !Printers)
    return;

/*
@@ -807,7 +807,7 @@

  • Figure out how many printers need an update...
    */
  • if (BrowseInterval > 0)
  • if (BrowseInterval > 0 && BrowseLocalProtocols)
    {
    int max_count; /* Maximum number to update */

@@ -885,7 +885,7 @@
}

/*

  • * Loop through all of the printers and send local updates as needed...

    • Loop through all of the printers and timeout old printers as needed...
      */

    for (p = (cupsd_printer_t *)cupsArrayFirst(Printers), write_printcap = 0;
    @@ -896,25 +896,24 @@

    • If this is a remote queue, see if it needs to be timed out...
      */
  • if (p->type & CUPS_PRINTER_DISCOVERED)

  • if ((p->type & CUPS_PRINTER_DISCOVERED) &&

  •    !(p->type & CUPS_PRINTER_IMPLICIT) &&
    
  • p->browse_expire < to)
    {

  •  if (p->browse_expire < to)
    
  •  {
    
  • cupsdAddEvent(CUPSD_EVENT_PRINTER_DELETED, p, NULL,

  •                  "%s \'%s\' deleted by directory services (timeout).",
    
  •         (p->type & CUPS_PRINTER_CLASS) ? "Class" : "Printer",
    
  •  cupsdAddEvent(CUPSD_EVENT_PRINTER_DELETED, p, NULL,
    
  •       "%s \'%s\' deleted by directory services (timeout).",
    
  •       (p->type & CUPS_PRINTER_CLASS) ? "Class" : "Printer",
    
  •       p->name);
    
  •  cupsdLogMessage(CUPSD_LOG_DEBUG,
    
  •         "Remote destination \"%s\" has timed out; "
    
  •         "deleting it...",
          p->name);
    
  •    cupsdLogMessage(CUPSD_LOG_DEBUG,
    
  •               "Remote destination \"%s\" has timed out; "
    
  •       "deleting it...",
    

- p->name);

  •    cupsArraySave(Printers);
    
  •    cupsdDeletePrinter(p, 1);
    
  •    cupsArrayRestore(Printers);
    
  • write_printcap = 1;
  •  }
    
  •  cupsArraySave(Printers);
    
  •  cupsdDeletePrinter(p, 1);
    
  •  cupsArrayRestore(Printers);
    
  •  write_printcap = 1;
    
    }
    }

@@ -1673,13 +1672,23 @@
newname[IPP_MAX_NAME], /* New name of printer /
*hptr, /
Pointer into hostname /
*sptr; /
Pointer into ServerName */

  • const char shortname; / Short queue name (queue) /
    char local_make_model[IPP_MAX_NAME];
    /
    Local make and model /
    cupsd_printer_t *p; /
    Printer information /
    const char *ipp_options, /
    ipp-options value /
    *lease_duration; /
    lease-duration value */
  • int is_class; /* Is this queue a class? */
  • cupsdLogMessage(CUPSD_LOG_DEBUG2,
  •              "process_browse_data(uri=\"%s\", host=\"%s\", "
    
  •     "resource=\"%s\", type=%x, state=%d, location=\"%s\", "
    
  •     "info=\"%s\", make_model=\"%s\", num_attrs=%d, attrs=%p)",
    
  •     uri, host, resource, type, state,
    
  •     location ? location : "(nil)", info ? info : "(nil)",
    
  •     make_model ? make_model : "(nil)", num_attrs, attrs);
    
    /*
    • Determine if the URI contains any illegal characters in it...
      */
      @@ -1688,9 +1697,7 @@
      (strncmp(resource, "/printers/", 10) &&
      strncmp(resource, "/classes/", 9)))
      {
  • cupsdLogMessage(CUPSD_LOG_ERROR,
  •                "process_browse_data: Bad printer URI in browse data: %s",
    
  •                uri);
    
  • cupsdLogMessage(CUPSD_LOG_ERROR, "Bad printer URI in browse data: %s", uri);
    return;
    }

@@ -1698,8 +1705,7 @@
(!strncmp(resource, "/printers/", 10) && strchr(resource + 10, '/')) ||
(!strncmp(resource, "/classes/", 9) && strchr(resource + 9, '/')))
{

  • cupsdLogMessage(CUPSD_LOG_ERROR,
  •                "process_browse_data: Bad resource in browse data: %s",
    
  • cupsdLogMessage(CUPSD_LOG_ERROR, "Bad resource in browse data: %s",
    resource);
    return;
    }
    @@ -1760,6 +1766,7 @@
    write_printcap = 0;
    hptr = strchr(host, '.');
    sptr = strchr(ServerName, '.');
  • is_class = type & CUPS_PRINTER_CLASS;

if (!ServerNameIsIP && sptr != NULL && hptr != NULL)
{
@@ -1779,7 +1786,7 @@
}
}

  • if (type & CUPS_PRINTER_CLASS)
  • if (is_class)
    {
    /*
  • Remote destination is a class...
    @@ -1790,208 +1797,137 @@
    else
    return;
  • if (hptr && !*hptr)
  •  _hptr = '.';         /_ Resource FQDN */
    
  • shortname = resource + 9;
  • }
  • else
  • {
  • /*
  • * Remote destination is a printer...
  • */
  • if ((p = cupsdFindDest(name)) == NULL && BrowseShortNames)
  • {
  •  if ((p = cupsdFindDest(resource + 9)) != NULL)
    
  •  {
    
  •    if (p->hostname && strcasecmp(p->hostname, host))
    
  • {
  • /*
  • \* Nope, this isn't the same host; if the hostname isn't the local host,
    
  • \* add it to the other class and then find a class using the full host
    
  • \* name...
    
  • */
    
  • if (!strncmp(resource, "/printers/", 10))
  •  snprintf(name, sizeof(name), "%s@%s", resource + 10, host);
    
  • else
  •  return;
    
  • if (p->type & CUPS_PRINTER_REMOTE)
    
  • {
    
  •   cupsdLogMessage(CUPSD_LOG_DEBUG,
    
  •                   "Renamed remote class \"%s\" to \"%s@%s\"...",
    
  •                   p->name, p->name, p->hostname);
    
  •   cupsdAddEvent(CUPSD_EVENT_PRINTER_DELETED, p, NULL,
    
  •                 "Class \'%s\' deleted by directory services.",
    
  •         p->name);
    
  • shortname = resource + 10;
  • }
  •        snprintf(newname, sizeof(newname), "%s@%s", p->name, p->hostname);
    
  •        cupsdRenamePrinter(p, newname);
    
  • if (hptr && !*hptr)
  • hptr = '.'; / Resource FQDN */
  •   cupsdAddEvent(CUPSD_EVENT_PRINTER_ADDED, p, NULL,
    
  •                 "Class \'%s\' added by directory services.",
    
  •         p->name);
    
  • }
    
  • if ((p = cupsdFindDest(name)) == NULL && BrowseShortNames)
  • {
  • /*
  • * Long name doesn't exist, try short name...
  • */
  •      p = NULL;
    
  • }
  • else if (!p->hostname)
  • {
  • /*
  • \* Hostname not set, so this must be a cached remote printer
    
  • \* that was created for a pending print job...
    
  • */
    
  • cupsdLogMessage(CUPSD_LOG_DEBUG, "process_browse_data: %s not found...",
  •                name);
    
  •      cupsdSetString(&p->hostname, host);
    
  • cupsdSetString(&p->uri, uri);
    
  • cupsdSetString(&p->device_uri, uri);
    
  •      update = 1;
    
  •    }
    
  •  }
    
  •  else
    
  •  {
    
  •   /*
    
  •    \* Use the short name for this shared class.
    

- */

  •    strlcpy(name, resource + 9, sizeof(name));
    
  •  }
    
  • }

  • else if (p && !p->hostname)

  • if ((p = cupsdFindDest(shortname)) == NULL)
    {
    /*

  •  \* Hostname not set, so this must be a cached remote printer
    
  •  \* that was created for a pending print job...
    
  •  * Short name doesn't exist, use it for this shared queue.
    

    */

  •  cupsdSetString(&p->hostname, host);
    
  •  cupsdSetString(&p->uri, uri);
    
  •  cupsdSetString(&p->device_uri, uri);
    
  •  update = 1;
    
  •  cupsdLogMessage(CUPSD_LOG_DEBUG2, "process_browse_data: %s not found...",
    
  •         shortname);
    
  •  strlcpy(name, shortname, sizeof(name));
    

    }

  • if (!p)

  • else
    {
    /*

  •  \* Class doesn't exist; add it...
    
  •  * Short name exists...
    

    */

  •  p = cupsdAddClass(name);
    
  •  cupsdLogMessage(CUPSD_LOG_DEBUG2,
    
  •                  "process_browse_data: %s found, type=%x, hostname=%s...",
    
  •         shortname, p->type, p->hostname ? p->hostname : "(nil)");
    
  •  cupsdLogMessage(CUPSD_LOG_DEBUG, "Added remote class \"%s\"...", name);
    
  •  if (p->type & CUPS_PRINTER_IMPLICIT)
    
  •    p = NULL;          /\* Don't replace implicit classes */
    
  •  else if (p->hostname && strcasecmp(p->hostname, host))
    
  •  {
    
  •   /*
    
  • * Short name exists but is for a different host. If this is a remote

  • * queue, rename it and use the long name...

  • */

  •  cupsdAddEvent(CUPSD_EVENT_PRINTER_ADDED, p, NULL,
    
  •                "Class \'%s\' added by directory services.", name);
    
  • if (p->type & CUPS_PRINTER_REMOTE)

  • {

  • cupsdLogMessage(CUPSD_LOG_DEBUG,
    
  •         "Renamed remote %s \"%s\" to \"%s@%s\"...",
    
  •         is_class ? "class" : "printer", p->name, p->name,
    
  •         p->hostname);
    
  • cupsdAddEvent(CUPSD_EVENT_PRINTER_DELETED, p, NULL,
    
  •       "%s \'%s\' deleted by directory services.",
    
  •       is_class ? "Class" : "Printer", p->name);
    
  • /*
    
  •  \* Force the URI to point to the real server...
    
  •  */
    
  • snprintf(newname, sizeof(newname), "%s@%s", p->name, p->hostname);
    
  • cupsdRenamePrinter(p, newname);
    
  •  p->type      = type & ~CUPS_PRINTER_REJECTING;
    
  •  p->accepting = 1;
    
  •  cupsdSetString(&p->uri, uri);
    
  •  cupsdSetString(&p->device_uri, uri);
    
  •  cupsdSetString(&p->hostname, host);
    
  • cupsdAddEvent(CUPSD_EVENT_PRINTER_ADDED, p, NULL,
    
  •       "%s \'%s\' added by directory services.",
    
  •       is_class ? "Class" : "Printer", p->name);
    
  • }

  •  update         = 1;
    
  •  write_printcap = 1;
    
  •   /*
    
  •    \* Force creation with long name...
    
  • */

  • p = NULL;
  •  }
    
    }
    }
    else
  • cupsdLogMessage(CUPSD_LOG_DEBUG2,
  •       "process_browse_data: %s found, type=%x, hostname=%s...",
    
  •       name, p->type, p->hostname ? p->hostname : "(nil)");
    
  • if (!p)
    {
    /*
  • * Remote destination is a printer...
    • Queue doesn't exist; add it...
      */
  • if (!strncmp(resource, "/printers/", 10))
  •  snprintf(name, sizeof(name), "%s@%s", resource + 10, host);
    
  • if (is_class)
  •  p = cupsdAddClass(name);
    
    else
  •  return;
    
  •  p = cupsdAddPrinter(name);
    
  • if (hptr && !*hptr)
  •  _hptr = '.';         /_ Resource FQDN */
    
  • cupsdClearString(&(p->hostname));
  • if ((p = cupsdFindDest(name)) == NULL && BrowseShortNames)
  • {
  •  if ((p = cupsdFindDest(resource + 10)) != NULL)
    
  •  {
    
  •    if (p->hostname && strcasecmp(p->hostname, host))
    
  • {
  • /*
  • \* Nope, this isn't the same host; if the hostname isn't the local host,
    
  • \* add it to the other printer and then find a printer using the full host
    
  • \* name...
    
  • */
    
  • cupsdLogMessage(CUPSD_LOG_DEBUG, "Added remote %s "%s"...",
  •                is_class ? "class" : "printer", name);
    
  • if (p->type & CUPS_PRINTER_REMOTE)
    
  • {
    
  •   cupsdLogMessage(CUPSD_LOG_DEBUG,
    
  •                   "Renamed remote printer \"%s\" to \"%s@%s\"...",
    
  •                   p->name, p->name, p->hostname);
    
  •   cupsdAddEvent(CUPSD_EVENT_PRINTER_DELETED, p, NULL,
    
  •                 "Printer \'%s\' deleted by directory services.",
    
  •         p->name);
    
  • cupsdAddEvent(CUPSD_EVENT_PRINTER_ADDED, p, NULL,
  •     "%s \'%s\' added by directory services.",
    
  •     is_class ? "Class" : "Printer", name);
    
  •        snprintf(newname, sizeof(newname), "%s@%s", p->name, p->hostname);
    
  •        cupsdRenamePrinter(p, newname);
    
  • /*
  • * Force the URI to point to the real server...
  • */
  •   cupsdAddEvent(CUPSD_EVENT_PRINTER_ADDED, p, NULL,
    
  •                 "Printer \'%s\' added by directory services.",
    
  •         p->name);
    
  • }
    
  • p->type = type & ~CUPS_PRINTER_REJECTING;
  • p->accepting = 1;
  • write_printcap = 1;
  • }
  •      p = NULL;
    
  • }
  • else if (!p->hostname)
  • {
  • /*
  • \* Hostname not set, so this must be a cached remote printer
    
  • \* that was created for a pending print job...
    
  • */
    
  • if (!p)
  • return;
  •      cupsdSetString(&p->hostname, host);
    
  • cupsdSetString(&p->uri, uri);
    
  • cupsdSetString(&p->device_uri, uri);
    
  •      update = 1;
    
  •    }
    
  •  }
    
  •  else
    
  •  {
    
  •   /*
    
  •    \* Use the short name for this shared printer.
    
  • */
  • if (!p->hostname)
  • {
  • /*
  • * Hostname not set, so this must be a cached remote printer
  • * that was created for a pending print job...
  • */
  •    strlcpy(name, resource + 10, sizeof(name));
    
  •  }
    
  • }
  • else if (p && !p->hostname)
  • {
  • /*
    
  •  \* Hostname not set, so this must be a cached remote printer
    
  •  \* that was created for a pending print job...
    

- */

  •  cupsdSetString(&p->hostname, host);
    
  •  cupsdSetString(&p->uri, uri);
    
  •  cupsdSetString(&p->device_uri, uri);
    
  •  update = 1;
    

- }

  • if (!p)
  • {
  • /*
    
  •  \* Printer doesn't exist; add it...
    

- */

- p = cupsdAddPrinter(name);

  •  cupsdAddEvent(CUPSD_EVENT_PRINTER_ADDED, p, NULL,
    

- "Printer '%s' added by directory services.", name);

- cupsdLogMessage(CUPSD_LOG_DEBUG, "Added remote printer "%s"...", name);

  • /*
    
  •  \* Force the URI to point to the real server...
    

- */

  •  p->type      = type & ~CUPS_PRINTER_REJECTING;
    
  •  p->accepting = 1;
    
  •  cupsdSetString(&p->hostname, host);
    
  •  cupsdSetString(&p->uri, uri);
    

- cupsdSetString(&p->device_uri, uri);

  •  write_printcap = 1;
    
  •  update         = 1;
    
  • }
  • cupsdSetString(&p->hostname, host);
  • cupsdSetString(&p->uri, uri);
  • cupsdSetString(&p->device_uri, uri);
  • update = 1;
    }

/*
@@ -2055,7 +1991,7 @@

if (!make_model || !make_model[0])
{

  • if (type & CUPS_PRINTER_CLASS)

  • if (is_class)
    snprintf(local_make_model, sizeof(local_make_model),
    "Remote Class on %s", host);
    else
    @@ -2109,7 +2045,7 @@
    {
    cupsdAddEvent(CUPSD_EVENT_PRINTER_DELETED, p, NULL,
    "%s '%s' deleted by directory services.",

  •     (type & CUPS_PRINTER_CLASS) ? "Class" : "Printer", p->name);
    
  •     is_class ? "Class" : "Printer", p->name);
    

    cupsdExpireSubscriptions(p, NULL);

Index: scheduler/printers.c

--- scheduler/printers.c (revision 7724)
+++ scheduler/printers.c (revision 7725)
@@ -133,6 +133,8 @@
if (!Printers)
Printers = cupsArrayNew(compare_printers, NULL);

  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •              "cupsdAddPrinter: Adding %s to Printers", p->name);
    

    cupsArrayAdd(Printers, p);

    if (!ImplicitPrinters)
    @@ -631,10 +633,17 @@

    • Remove the printer from the list...
      */
  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •              "cupsdDeletePrinter: Removing %s from Printers", p->name);
    

    cupsArrayRemove(Printers, p);

    if (p->type & CUPS_PRINTER_IMPLICIT)

  • {

  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •       "cupsdDeletePrinter: Removing %s from ImplicitPrinters",
    
  •       p->name);
    

    cupsArrayRemove(ImplicitPrinters, p);

  • }

/*

  • Remove the dummy interface/icon/option files under IRIX...
    @@ -1256,10 +1265,17 @@

  • Remove the printer from the array(s) first...
    */

  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •              "cupsdRenamePrinter: Removing %s from Printers", p->name);
    

    cupsArrayRemove(Printers, p);

    if (p->type & CUPS_PRINTER_IMPLICIT)

  • {

  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •       "cupsdRenamePrinter: Removing %s from ImplicitPrinters",
    
  •       p->name);
    

    cupsArrayRemove(ImplicitPrinters, p);

  • }

/*

  • Rename the printer type...
    @@ -1287,10 +1303,17 @@

  • Add the printer back to the printer array(s)...
    */

  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •              "cupsdRenamePrinter: Adding %s to Printers", p->name);
    

    cupsArrayAdd(Printers, p);

    if (p->type & CUPS_PRINTER_IMPLICIT)

  • {

  • cupsdLogMessage(CUPSD_LOG_DEBUG2,

  •       "cupsdRenamePrinter: Adding %s to ImplicitPrinters",
    
  •       p->name);
    

    cupsArrayAdd(ImplicitPrinters, p);

  • }
    }

@@ -3372,7 +3395,8 @@

  • super/type cost program
    

    */

  • if (sscanf(filter, "%15[^/]/%31s%d%1023s", super, type, &cost, program) != 4)

  • if (sscanf(filter, "%15[^/]/%31s%d%*[ \t]%1023[^\n]", super, type, &cost,

  •         program) != 4)
    

    {
    cupsdLogMessage(CUPSD_LOG_ERROR, "%s: invalid filter string "%s"!",
    p->name, filter);

    Index: scheduler/main.c

    --- scheduler/main.c (revision 7724)
    +++ scheduler/main.c (revision 7725)
    @@ -910,7 +910,7 @@
    #endif /* HAVE_LDAP */
    }

  • if (Browsing && BrowseLocalProtocols && current_time > browse_time)

  • if (Browsing && current_time > browse_time)
    {
    cupsdSendBrowseList();
    browse_time = current_time;
    Index: scheduler/classes.c
    ===================================================================
    --- scheduler/classes.c (revision 7724)
    +++ scheduler/classes.c (revision 7725)
    @@ -210,7 +210,8 @@
    c = (cupsd_printer_t *)cupsArrayNext(ImplicitPrinters))
    if (c->num_printers == 0)
    {

  •  cupsArrayRemove(ImplicitPrinters, c);
    
  •  cupsdLogMessage(CUPSD_LOG_DEBUG, "Deleting implicit class \"%s\"...",
    
  •                  c->name);
    

    cupsdDeletePrinter(c, 0);
    }
    }

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

1 participant