For Michael Pfeiffer, ready for beta...
git-svn-id: file:///srv/svn/repos/haiku/trunk/current@1108 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -7,6 +7,8 @@
|
|||||||
// very specific functions, but generally useful (could be here because of a
|
// very specific functions, but generally useful (could be here because of a
|
||||||
// lack in the APIs, or just sheer lazyness :))
|
// lack in the APIs, or just sheer lazyness :))
|
||||||
//
|
//
|
||||||
|
// Author
|
||||||
|
// Ithamar R. Adema
|
||||||
//
|
//
|
||||||
// This application and all source files used in its construction, except
|
// This application and all source files used in its construction, except
|
||||||
// where noted, are licensed under the MIT License, and have been written
|
// where noted, are licensed under the MIT License, and have been written
|
||||||
|
|||||||
@@ -1,10 +1,76 @@
|
|||||||
|
/*****************************************************************************/
|
||||||
|
// BeUtils.cpp
|
||||||
|
//
|
||||||
|
// Version: 1.0.0d1
|
||||||
|
//
|
||||||
|
// Several utilities for writing applications for the BeOS. It are small
|
||||||
|
// very specific functions, but generally useful (could be here because of a
|
||||||
|
// lack in the APIs, or just sheer lazyness :))
|
||||||
|
//
|
||||||
|
// Authors
|
||||||
|
// Ithamar R. Adema
|
||||||
|
// Michael Pfeiffer
|
||||||
|
//
|
||||||
|
// This application and all source files used in its construction, except
|
||||||
|
// where noted, are licensed under the MIT License, and have been written
|
||||||
|
// and are:
|
||||||
|
//
|
||||||
|
// Copyright (c) 2001 OpenBeOS Project
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||||
|
// copy of this software and associated documentation files (the "Software"),
|
||||||
|
// to deal in the Software without restriction, including without limitation
|
||||||
|
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||||
|
// and/or sell copies of the Software, and to permit persons to whom the
|
||||||
|
// Software is furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included
|
||||||
|
// in all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||||
|
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||||
|
// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||||
|
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||||
|
// DEALINGS IN THE SOFTWARE.
|
||||||
|
/*****************************************************************************/
|
||||||
|
|
||||||
#ifndef BEUTILS_H
|
#ifndef BEUTILS_H
|
||||||
#define BEUTILS_H
|
#define BEUTILS_H
|
||||||
|
|
||||||
#include <FindDirectory.h>
|
#include <FindDirectory.h>
|
||||||
#include <Path.h>
|
#include <Path.h>
|
||||||
|
#include <SupportDefs.h>
|
||||||
|
|
||||||
status_t TestForAddonExistence(const char* name, directory_which which,
|
status_t TestForAddonExistence(const char* name, directory_which which,
|
||||||
const char* section, BPath& outPath);
|
const char* section, BPath& outPath);
|
||||||
|
|
||||||
|
// Reference counted object
|
||||||
|
class Object {
|
||||||
|
private:
|
||||||
|
volatile int32 fRefCount;
|
||||||
|
|
||||||
|
public:
|
||||||
|
// After construction reference count is 1
|
||||||
|
Object() : fRefCount(1) { }
|
||||||
|
// dtor should be private, but ie. ObjectList requires a public dtor!
|
||||||
|
virtual ~Object() { };
|
||||||
|
|
||||||
|
// thread-safe as long as thread that calls acquire has already
|
||||||
|
// a reference to the object
|
||||||
|
void Acquire() {
|
||||||
|
atomic_add(&fRefCount, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Release() {
|
||||||
|
atomic_add(&fRefCount, -1);
|
||||||
|
if (fRefCount == 0) {
|
||||||
|
delete this; return true;
|
||||||
|
} else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -17,6 +17,8 @@ Server
|
|||||||
PrintServerApp.Scripting.cpp
|
PrintServerApp.Scripting.cpp
|
||||||
Printer.Scripting.cpp
|
Printer.Scripting.cpp
|
||||||
Printer.cpp
|
Printer.cpp
|
||||||
|
ResourceManager.cpp
|
||||||
|
Jobs.cpp
|
||||||
BeUtils.cpp
|
BeUtils.cpp
|
||||||
;
|
;
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,307 @@
|
|||||||
|
/*****************************************************************************/
|
||||||
|
// Jobs
|
||||||
|
//
|
||||||
|
// Author
|
||||||
|
// Michael Pfeiffer
|
||||||
|
//
|
||||||
|
// This application and all source files used in its construction, except
|
||||||
|
// where noted, are licensed under the MIT License, and have been written
|
||||||
|
// and are:
|
||||||
|
//
|
||||||
|
// Copyright (c) 2002 OpenBeOS Project
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||||
|
// copy of this software and associated documentation files (the "Software"),
|
||||||
|
// to deal in the Software without restriction, including without limitation
|
||||||
|
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||||
|
// and/or sell copies of the Software, and to permit persons to whom the
|
||||||
|
// Software is furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included
|
||||||
|
// in all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||||
|
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||||
|
// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||||
|
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||||
|
// DEALINGS IN THE SOFTWARE.
|
||||||
|
/*****************************************************************************/
|
||||||
|
|
||||||
|
|
||||||
|
#include "pr_server.h"
|
||||||
|
#include "Jobs.h"
|
||||||
|
#include "PrintServerApp.h"
|
||||||
|
|
||||||
|
// posix
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
// BeOS
|
||||||
|
#include <Application.h>
|
||||||
|
#include <Autolock.h>
|
||||||
|
#include <Node.h>
|
||||||
|
#include <NodeInfo.h>
|
||||||
|
#include <NodeMonitor.h>
|
||||||
|
|
||||||
|
|
||||||
|
Job::Job(const BEntry& job, BHandler* handler)
|
||||||
|
: fHandler(handler)
|
||||||
|
, fTime(-1)
|
||||||
|
, fStatus(kUnknown)
|
||||||
|
, fPrinter(NULL)
|
||||||
|
{
|
||||||
|
// store light weight versions of BEntry and BNode
|
||||||
|
job.GetRef(&fEntry);
|
||||||
|
job.GetNodeRef(&fNode);
|
||||||
|
|
||||||
|
BNode node(&job);
|
||||||
|
if (node.InitCheck() != B_OK) return;
|
||||||
|
|
||||||
|
BNodeInfo info(&node);
|
||||||
|
char mimeType[256];
|
||||||
|
BString status;
|
||||||
|
|
||||||
|
// Is job a spool file?
|
||||||
|
if (info.InitCheck() == B_OK /*&&
|
||||||
|
info.GetType(mimeType) == B_OK &&
|
||||||
|
strcmp(mimeType, PSRV_SPOOL_FILETYPE) == 0 &&
|
||||||
|
node.ReadAttr(PSRV_SPOOL_ATTR_STATUS, B_STRING_TYPE, 0, status, sizeof(status))*/) {
|
||||||
|
if (node.ReadAttrString(PSRV_SPOOL_ATTR_STATUS, &status) != B_OK) {
|
||||||
|
status = "";
|
||||||
|
}
|
||||||
|
// read status attribute
|
||||||
|
UpdateStatus(status.String());
|
||||||
|
// Now get file name and creation time from file name
|
||||||
|
fTime = 0;
|
||||||
|
BEntry entry(job);
|
||||||
|
char name[B_FILE_NAME_LENGTH];
|
||||||
|
if (entry.InitCheck() == B_OK && entry.GetName(name) == B_OK) {
|
||||||
|
fName = name;
|
||||||
|
// search for last '@' in file name
|
||||||
|
char* p = NULL, *c = name;
|
||||||
|
while ((c = strchr(c, '@')) != NULL) {
|
||||||
|
p = c; c ++;
|
||||||
|
}
|
||||||
|
// and get time from file name
|
||||||
|
fTime = atoi(p+1);
|
||||||
|
}
|
||||||
|
// start watching if everything is ok
|
||||||
|
StartNodeWatching();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// conversion from string representation of status to JobStatus constant
|
||||||
|
void Job::UpdateStatus(const char* status) {
|
||||||
|
if (strcmp(status, PSRV_JOB_STATUS_WAITING) == 0) fStatus = kWaiting;
|
||||||
|
else if (strcmp(status, PSRV_JOB_STATUS_PROCESSING) == 0) fStatus = kProcessing;
|
||||||
|
else if (strcmp(status, PSRV_JOB_STATUS_FAILED) == 0) fStatus = kFailed;
|
||||||
|
else fStatus = kUnknown;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Write to status attribute of node
|
||||||
|
void Job::UpdateStatusAttribute(const char* status) {
|
||||||
|
BNode node(&fEntry);
|
||||||
|
if (node.InitCheck() == B_OK) {
|
||||||
|
node.WriteAttr(PSRV_SPOOL_ATTR_STATUS, B_STRING_TYPE, 0, status, strlen(status)+1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set status of object and optionally write to attribute of node
|
||||||
|
void Job::SetStatus(JobStatus s, bool writeToNode) {
|
||||||
|
fStatus = s;
|
||||||
|
if (!writeToNode) return;
|
||||||
|
switch (s) {
|
||||||
|
case kWaiting: UpdateStatusAttribute(PSRV_JOB_STATUS_WAITING); break;
|
||||||
|
case kProcessing: UpdateStatusAttribute(PSRV_JOB_STATUS_PROCESSING); break;
|
||||||
|
case kFailed: UpdateStatusAttribute(PSRV_JOB_STATUS_FAILED); break;
|
||||||
|
default: break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Synchronize file attribute with member variable
|
||||||
|
void Job::UpdateAttribute() {
|
||||||
|
BNode node(&fEntry);
|
||||||
|
BString status;
|
||||||
|
if (node.InitCheck() == B_OK &&
|
||||||
|
node.ReadAttrString(PSRV_SPOOL_ATTR_STATUS, &status) == B_OK) {
|
||||||
|
UpdateStatus(status.String());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Job::Remove() {
|
||||||
|
BEntry entry(&fEntry);
|
||||||
|
if (entry.InitCheck() == B_OK) entry.Remove();
|
||||||
|
}
|
||||||
|
|
||||||
|
void Job::StartNodeWatching() {
|
||||||
|
watch_node(&fNode, B_WATCH_ATTR, fHandler, be_app);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Job::StopNodeWatching() {
|
||||||
|
watch_node(&fNode, B_STOP_WATCHING, fHandler, be_app);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Implementation of Folder
|
||||||
|
|
||||||
|
// BObjectList CompareFunction
|
||||||
|
int Folder::AscendingByTime(const Job* a, const Job* b) {
|
||||||
|
return a->Time() - b->Time();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Folder::AddJob(BEntry& entry) {
|
||||||
|
Job* job = new Job(entry, this);
|
||||||
|
if (job->InitCheck() == B_OK) {
|
||||||
|
fJobs.AddItem(job);
|
||||||
|
if (job->IsWaiting()) NotifyPrinter();
|
||||||
|
return true;
|
||||||
|
} else {
|
||||||
|
job->Release();
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// simplified assumption that ino_t identifies job file
|
||||||
|
// will probabely not work in all cases with link to a file on another volume???
|
||||||
|
Job* Folder::Find(ino_t node) {
|
||||||
|
for (int i = 0; i < fJobs.CountItems(); i ++) {
|
||||||
|
Job* job = fJobs.ItemAt(i);
|
||||||
|
if (job->NodeRef().node == node) return job;
|
||||||
|
}
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Folder::EntryCreated(BMessage* msg) {
|
||||||
|
BString name;
|
||||||
|
BEntry entry;
|
||||||
|
if (msg->FindString("name", &name) == B_OK &&
|
||||||
|
fSpoolDir.FindEntry(name.String(), &entry) == B_OK) {
|
||||||
|
BAutolock lock(gLock);
|
||||||
|
if (lock.IsLocked() && AddJob(entry)) {
|
||||||
|
fJobs.SortItems(AscendingByTime);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Folder::EntryRemoved(BMessage* msg) {
|
||||||
|
ino_t node;
|
||||||
|
if (msg->FindInt64("node", &node) == B_OK) {
|
||||||
|
Job* job = Find(node);
|
||||||
|
if (job) {
|
||||||
|
fJobs.RemoveItem(job);
|
||||||
|
job->StopNodeWatching();
|
||||||
|
job->Release();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Folder::AttributeChanged(BMessage* msg) {
|
||||||
|
ino_t node;
|
||||||
|
if (msg->FindInt64("node", &node) == B_OK) {
|
||||||
|
Job* job = Find(node);
|
||||||
|
if (job) {
|
||||||
|
job->UpdateAttribute();
|
||||||
|
if (job->IsWaiting()) NotifyPrinter();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Folder::HandleNodeMonitorMessage(BMessage* msg) {
|
||||||
|
BAutolock lock(gLock);
|
||||||
|
if (!lock.IsLocked()) return;
|
||||||
|
int32 opcode;
|
||||||
|
if (msg->FindInt32("opcode", &opcode) != B_OK) return;
|
||||||
|
switch (opcode) {
|
||||||
|
case B_ENTRY_CREATED: // add to fJobs
|
||||||
|
EntryCreated(msg);
|
||||||
|
break;
|
||||||
|
case B_ENTRY_REMOVED: // remove from fJobs
|
||||||
|
EntryRemoved(msg);
|
||||||
|
break;
|
||||||
|
case B_ATTR_CHANGED: // notify Printer if status has changed to Waiting
|
||||||
|
AttributeChanged(msg);
|
||||||
|
break;
|
||||||
|
default: // nothing to do
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Folder::NotifyPrinter() {
|
||||||
|
be_app_messenger.SendMessage(PSRV_PRINT_SPOOLED_JOB);
|
||||||
|
}
|
||||||
|
|
||||||
|
// initial setup of job list
|
||||||
|
void Folder::SetupJobList() {
|
||||||
|
if (fSpoolDir.InitCheck() == B_OK) {
|
||||||
|
fSpoolDir.Rewind();
|
||||||
|
|
||||||
|
BEntry entry;
|
||||||
|
while (fSpoolDir.GetNextEntry(&entry) == B_OK) {
|
||||||
|
AddJob(entry);
|
||||||
|
}
|
||||||
|
fJobs.SortItems(AscendingByTime);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Folder::Folder(const BDirectory& spoolDir)
|
||||||
|
: fSpoolDir(spoolDir)
|
||||||
|
, fJobs()
|
||||||
|
{
|
||||||
|
BAutolock lock(gLock);
|
||||||
|
if (!lock.IsLocked()) return;
|
||||||
|
// add this handler to the application for node monitoring
|
||||||
|
be_app->AddHandler(this);
|
||||||
|
|
||||||
|
SetupJobList();
|
||||||
|
|
||||||
|
// start watching the spooler directory
|
||||||
|
node_ref ref;
|
||||||
|
spoolDir.GetNodeRef(&ref);
|
||||||
|
watch_node(&ref, B_WATCH_DIRECTORY, this, be_app);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Folder::~Folder() {
|
||||||
|
if (!gLock->Lock()) return;
|
||||||
|
// stop node watching for jobs
|
||||||
|
for (int i = 0; i < fJobs.CountItems(); i ++) {
|
||||||
|
Job* job = fJobs.ItemAt(i);
|
||||||
|
job->StopNodeWatching();
|
||||||
|
job->Release();
|
||||||
|
}
|
||||||
|
// stop node watching for spooler directory
|
||||||
|
node_ref ref;
|
||||||
|
fSpoolDir.GetNodeRef(&ref);
|
||||||
|
watch_node(&ref, B_STOP_WATCHING, this, be_app);
|
||||||
|
// stop sending notifications to this handler
|
||||||
|
stop_watching(this, be_app);
|
||||||
|
gLock->Unlock();
|
||||||
|
|
||||||
|
if (be_app->Lock()) {
|
||||||
|
// and remove it from application
|
||||||
|
be_app->RemoveHandler(this);
|
||||||
|
be_app->Unlock();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void Folder::MessageReceived(BMessage* msg) {
|
||||||
|
if (msg->what == B_NODE_MONITOR) {
|
||||||
|
HandleNodeMonitorMessage(msg);
|
||||||
|
} else {
|
||||||
|
inherited::MessageReceived(msg);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Job* Folder::GetNextJob() {
|
||||||
|
for (int i = 0; i < fJobs.CountItems(); i ++) {
|
||||||
|
Job* job = fJobs.ItemAt(i);
|
||||||
|
if (job->IsWaiting()) {
|
||||||
|
job->Acquire(); return job;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
@@ -0,0 +1,122 @@
|
|||||||
|
/*****************************************************************************/
|
||||||
|
// Jobs
|
||||||
|
//
|
||||||
|
// Author
|
||||||
|
// Michael Pfeiffer
|
||||||
|
//
|
||||||
|
// This application and all source files used in its construction, except
|
||||||
|
// where noted, are licensed under the MIT License, and have been written
|
||||||
|
// and are:
|
||||||
|
//
|
||||||
|
// Copyright (c) 2002 OpenBeOS Project
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||||
|
// copy of this software and associated documentation files (the "Software"),
|
||||||
|
// to deal in the Software without restriction, including without limitation
|
||||||
|
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||||
|
// and/or sell copies of the Software, and to permit persons to whom the
|
||||||
|
// Software is furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included
|
||||||
|
// in all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||||
|
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||||
|
// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||||
|
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||||
|
// DEALINGS IN THE SOFTWARE.
|
||||||
|
/*****************************************************************************/
|
||||||
|
|
||||||
|
#ifndef _JOBS_H
|
||||||
|
#define _JOBS_H
|
||||||
|
|
||||||
|
#include "BeUtils.h"
|
||||||
|
#include "ObjectList.h"
|
||||||
|
#include <Directory.h>
|
||||||
|
#include <Entry.h>
|
||||||
|
#include <Handler.h>
|
||||||
|
#include <String.h>
|
||||||
|
#include <StorageDefs.h>
|
||||||
|
|
||||||
|
enum JobStatus {
|
||||||
|
kWaiting,
|
||||||
|
kProcessing,
|
||||||
|
kFailed,
|
||||||
|
kUnknown,
|
||||||
|
};
|
||||||
|
|
||||||
|
class Printer;
|
||||||
|
|
||||||
|
class Job : public Object {
|
||||||
|
private:
|
||||||
|
BHandler* fHandler;
|
||||||
|
BString fName;
|
||||||
|
node_ref fNode;
|
||||||
|
entry_ref fEntry;
|
||||||
|
JobStatus fStatus;
|
||||||
|
long fTime;
|
||||||
|
Printer* fPrinter;
|
||||||
|
|
||||||
|
void UpdateStatus(const char* status);
|
||||||
|
void UpdateStatusAttribute(const char* status);
|
||||||
|
|
||||||
|
public:
|
||||||
|
Job(const BEntry& entry, BHandler* handler);
|
||||||
|
|
||||||
|
status_t InitCheck() const { return fTime >= 0 ? B_OK : B_ERROR; }
|
||||||
|
|
||||||
|
// accessors
|
||||||
|
const BString& Name() const { return fName; }
|
||||||
|
JobStatus Status() const { return fStatus; }
|
||||||
|
long Time() const { return fTime; }
|
||||||
|
const node_ref& NodeRef() const { return fNode; }
|
||||||
|
const entry_ref& EntryRef() const { return fEntry; }
|
||||||
|
bool IsWaiting() const { return fStatus == kWaiting; }
|
||||||
|
Printer* GetPrinter() const { return fPrinter; }
|
||||||
|
|
||||||
|
// modification
|
||||||
|
void SetPrinter(Printer* p) { fPrinter = p; }
|
||||||
|
void SetStatus(JobStatus s, bool writeToNode = true);
|
||||||
|
void UpdateAttribute();
|
||||||
|
void Remove();
|
||||||
|
|
||||||
|
void StartNodeWatching();
|
||||||
|
void StopNodeWatching();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
class Folder : public BHandler {
|
||||||
|
typedef BHandler inherited;
|
||||||
|
|
||||||
|
private:
|
||||||
|
BDirectory fSpoolDir;
|
||||||
|
BObjectList<Job> fJobs;
|
||||||
|
|
||||||
|
static int AscendingByTime(const Job* a, const Job* b);
|
||||||
|
|
||||||
|
bool AddJob(BEntry& entry);
|
||||||
|
Job* Find(ino_t node);
|
||||||
|
|
||||||
|
// node monitor handling
|
||||||
|
void EntryCreated(BMessage* msg);
|
||||||
|
void EntryRemoved(BMessage* msg);
|
||||||
|
void AttributeChanged(BMessage* msg);
|
||||||
|
void HandleNodeMonitorMessage(BMessage* msg);
|
||||||
|
|
||||||
|
void NotifyPrinter();
|
||||||
|
|
||||||
|
void SetupJobList();
|
||||||
|
|
||||||
|
public:
|
||||||
|
Folder(const BDirectory& spoolDir);
|
||||||
|
~Folder();
|
||||||
|
|
||||||
|
void MessageReceived(BMessage* msg);
|
||||||
|
|
||||||
|
// Caller is responsible to set the status of the job appropriately
|
||||||
|
// and to release the object when done
|
||||||
|
Job* GetNextJob();
|
||||||
|
};
|
||||||
|
#endif
|
||||||
Binary file not shown.
@@ -6,12 +6,9 @@
|
|||||||
// The print_server manages the communication between applications and the
|
// The print_server manages the communication between applications and the
|
||||||
// printer and transport drivers.
|
// printer and transport drivers.
|
||||||
//
|
//
|
||||||
//
|
// Authors
|
||||||
//
|
// Ithamar R. Adema
|
||||||
// TODO:
|
// Michael Pfeiffer
|
||||||
// Handle spooled jobs at startup
|
|
||||||
// Handle printer status (asked to print a spooled job but printer busy)
|
|
||||||
//
|
|
||||||
//
|
//
|
||||||
// This application and all source files used in its construction, except
|
// This application and all source files used in its construction, except
|
||||||
// where noted, are licensed under the MIT License, and have been written
|
// where noted, are licensed under the MIT License, and have been written
|
||||||
@@ -53,12 +50,16 @@
|
|||||||
|
|
||||||
struct AsyncThreadParams {
|
struct AsyncThreadParams {
|
||||||
Printer* printer;
|
Printer* printer;
|
||||||
BMessage message;
|
BMessage* message;
|
||||||
|
|
||||||
AsyncThreadParams(Printer* p, BMessage* m)
|
AsyncThreadParams(Printer* p, BMessage* m)
|
||||||
: printer(p)
|
: printer(p)
|
||||||
, message(*m)
|
, message(m)
|
||||||
{ }
|
{ }
|
||||||
|
|
||||||
|
~AsyncThreadParams() {
|
||||||
|
delete message;
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
status_t PrintServerApp::async_thread(void* data)
|
status_t PrintServerApp::async_thread(void* data)
|
||||||
@@ -66,7 +67,7 @@ status_t PrintServerApp::async_thread(void* data)
|
|||||||
AsyncThreadParams* p = (AsyncThreadParams*)data;
|
AsyncThreadParams* p = (AsyncThreadParams*)data;
|
||||||
|
|
||||||
Printer* printer = p->printer;
|
Printer* printer = p->printer;
|
||||||
BMessage* msg = &p->message;
|
BMessage* msg = p->message;
|
||||||
|
|
||||||
switch (msg->what) {
|
switch (msg->what) {
|
||||||
// Handle showing the page config dialog
|
// Handle showing the page config dialog
|
||||||
@@ -131,10 +132,6 @@ void PrintServerApp::AsyncHandleMessage(BMessage* msg)
|
|||||||
|
|
||||||
void PrintServerApp::Handle_BeOSR5_Message(BMessage* msg)
|
void PrintServerApp::Handle_BeOSR5_Message(BMessage* msg)
|
||||||
{
|
{
|
||||||
printf("PrintServerApp::Handle_BeOSR5_Message\n");
|
|
||||||
msg->PrintToStream();
|
|
||||||
fflush(stdout);
|
|
||||||
|
|
||||||
switch(msg->what) {
|
switch(msg->what) {
|
||||||
// Get currently selected printer
|
// Get currently selected printer
|
||||||
case PSRV_GET_ACTIVE_PRINTER: {
|
case PSRV_GET_ACTIVE_PRINTER: {
|
||||||
@@ -186,18 +183,12 @@ void PrintServerApp::Handle_BeOSR5_Message(BMessage* msg)
|
|||||||
|
|
||||||
case PSRV_SHOW_PAGE_SETUP:
|
case PSRV_SHOW_PAGE_SETUP:
|
||||||
case PSRV_SHOW_PRINT_SETUP:
|
case PSRV_SHOW_PRINT_SETUP:
|
||||||
AsyncHandleMessage(msg);
|
AsyncHandleMessage(DetachCurrentMessage());
|
||||||
break;
|
break;
|
||||||
|
|
||||||
// Tell printer addon to print a spooled job
|
// Tell printer addon to print a spooled job
|
||||||
case PSRV_PRINT_SPOOLED_JOB: {
|
case PSRV_PRINT_SPOOLED_JOB:
|
||||||
BString name, jobpath;
|
HandleSpooledJobs();
|
||||||
if (msg->FindString("Spool File",&jobpath) == B_OK &&
|
|
||||||
msg->FindString("JobName", &name) == B_OK) {
|
|
||||||
// Handle the spooled job
|
|
||||||
HandleSpooledJob(name.String(), jobpath.String());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,6 +6,8 @@
|
|||||||
// The print_server manages the communication between applications and the
|
// The print_server manages the communication between applications and the
|
||||||
// printer and transport drivers.
|
// printer and transport drivers.
|
||||||
//
|
//
|
||||||
|
// Author
|
||||||
|
// Ithamar R. Adema
|
||||||
//
|
//
|
||||||
// This application and all source files used in its construction, except
|
// This application and all source files used in its construction, except
|
||||||
// where noted, are licensed under the MIT License, and have been written
|
// where noted, are licensed under the MIT License, and have been written
|
||||||
@@ -105,7 +107,7 @@ PrintServerApp::HandleScriptingCommand(BMessage* msg)
|
|||||||
case B_DELETE_PROPERTY: {
|
case B_DELETE_PROPERTY: {
|
||||||
Printer* printer = GetPrinterFromSpecifier(&spec);
|
Printer* printer = GetPrinterFromSpecifier(&spec);
|
||||||
status_t rc = B_BAD_VALUE;
|
status_t rc = B_BAD_VALUE;
|
||||||
|
|
||||||
if (printer != NULL && (rc=printer->Remove()) == B_OK) {
|
if (printer != NULL && (rc=printer->Remove()) == B_OK) {
|
||||||
printer->Release();
|
printer->Release();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,12 +6,9 @@
|
|||||||
// The print_server manages the communication between applications and the
|
// The print_server manages the communication between applications and the
|
||||||
// printer and transport drivers.
|
// printer and transport drivers.
|
||||||
//
|
//
|
||||||
//
|
// Authors
|
||||||
//
|
// Ithamar R. Adema
|
||||||
// TODO:
|
// Michael Pfeiffer
|
||||||
// Handle spooled jobs at startup
|
|
||||||
// Handle printer status (asked to print a spooled job but printer busy)
|
|
||||||
//
|
|
||||||
//
|
//
|
||||||
// This application and all source files used in its construction, except
|
// This application and all source files used in its construction, except
|
||||||
// where noted, are licensed under the MIT License, and have been written
|
// where noted, are licensed under the MIT License, and have been written
|
||||||
@@ -45,23 +42,26 @@
|
|||||||
#include "pr_server.h"
|
#include "pr_server.h"
|
||||||
|
|
||||||
// BeOS API
|
// BeOS API
|
||||||
#include <FindDirectory.h>
|
|
||||||
#include <NodeMonitor.h>
|
|
||||||
#include <Directory.h>
|
|
||||||
#include <PrintJob.h>
|
|
||||||
#include <NodeInfo.h>
|
|
||||||
#include <String.h>
|
|
||||||
#include <Roster.h>
|
|
||||||
#include <image.h>
|
|
||||||
#include <Alert.h>
|
#include <Alert.h>
|
||||||
#include <Path.h>
|
#include <Autolock.h>
|
||||||
|
#include <Directory.h>
|
||||||
#include <File.h>
|
#include <File.h>
|
||||||
|
#include <image.h>
|
||||||
|
#include <FindDirectory.h>
|
||||||
#include <Mime.h>
|
#include <Mime.h>
|
||||||
|
#include <NodeInfo.h>
|
||||||
|
#include <NodeMonitor.h>
|
||||||
|
#include <Path.h>
|
||||||
|
#include <Roster.h>
|
||||||
|
#include <PrintJob.h>
|
||||||
|
#include <String.h>
|
||||||
|
|
||||||
// ANSI C
|
// ANSI C
|
||||||
#include <stdio.h> //for printf
|
#include <stdio.h> //for printf
|
||||||
#include <unistd.h> //for unlink
|
#include <unistd.h> //for unlink
|
||||||
|
|
||||||
|
BLocker *gLock = NULL;
|
||||||
|
|
||||||
// ---------------------------------------------------------------
|
// ---------------------------------------------------------------
|
||||||
typedef struct _printer_data {
|
typedef struct _printer_data {
|
||||||
char defaultPrinterName[256];
|
char defaultPrinterName[256];
|
||||||
@@ -83,16 +83,17 @@ typedef char* (*add_printer_func_t)(const char* printer_name);
|
|||||||
int
|
int
|
||||||
main()
|
main()
|
||||||
{
|
{
|
||||||
|
gLock = new BLocker();
|
||||||
// Create our application object
|
// Create our application object
|
||||||
status_t rc = B_OK;
|
status_t rc = B_OK;
|
||||||
new PrintServerApp(&rc);
|
PrintServerApp print_server(&rc);
|
||||||
|
|
||||||
// If all went fine, let's start it
|
// If all went fine, let's start it
|
||||||
if (rc == B_OK) {
|
if (rc == B_OK) {
|
||||||
be_app->Run();
|
print_server.Run();
|
||||||
}
|
}
|
||||||
|
|
||||||
delete be_app;
|
delete gLock;
|
||||||
|
|
||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
@@ -111,10 +112,14 @@ main()
|
|||||||
PrintServerApp::PrintServerApp(status_t* err)
|
PrintServerApp::PrintServerApp(status_t* err)
|
||||||
: Inherited(PSRV_SIGNATURE_TYPE, err),
|
: Inherited(PSRV_SIGNATURE_TYPE, err),
|
||||||
fSelectedIconMini(BRect(0,0,B_MINI_ICON-1,B_MINI_ICON-1), B_CMAP8),
|
fSelectedIconMini(BRect(0,0,B_MINI_ICON-1,B_MINI_ICON-1), B_CMAP8),
|
||||||
fSelectedIconLarge(BRect(0,0,B_LARGE_ICON-1,B_LARGE_ICON-1), B_CMAP8)
|
fSelectedIconLarge(BRect(0,0,B_LARGE_ICON-1,B_LARGE_ICON-1), B_CMAP8),
|
||||||
|
fNumberOfPrinters(0),
|
||||||
|
fNoPrinterAvailable(0)
|
||||||
{
|
{
|
||||||
// If our superclass initialized ok
|
// If our superclass initialized ok
|
||||||
if (*err == B_OK) {
|
if (*err == B_OK) {
|
||||||
|
fNoPrinterAvailable = create_sem(1, "");
|
||||||
|
|
||||||
// let us try as well
|
// let us try as well
|
||||||
SetupPrinterList();
|
SetupPrinterList();
|
||||||
RetrieveDefaultPrinter();
|
RetrieveDefaultPrinter();
|
||||||
@@ -123,6 +128,9 @@ PrintServerApp::PrintServerApp(status_t* err)
|
|||||||
BMimeType type(PRNT_SIGNATURE_TYPE);
|
BMimeType type(PRNT_SIGNATURE_TYPE);
|
||||||
type.GetIcon(&fSelectedIconMini, B_MINI_ICON);
|
type.GetIcon(&fSelectedIconMini, B_MINI_ICON);
|
||||||
type.GetIcon(&fSelectedIconLarge, B_LARGE_ICON);
|
type.GetIcon(&fSelectedIconLarge, B_LARGE_ICON);
|
||||||
|
|
||||||
|
// Start handling of spooled files
|
||||||
|
PostMessage(PSRV_PRINT_SPOOLED_JOB);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -141,11 +149,69 @@ bool PrintServerApp::QuitRequested()
|
|||||||
::watch_node(&nref, B_STOP_WATCHING, be_app_messenger);
|
::watch_node(&nref, B_STOP_WATCHING, be_app_messenger);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Release all printers
|
||||||
|
Printer* printer;
|
||||||
|
while ((printer = Printer::At(0)) != NULL) {
|
||||||
|
Printer::Remove(printer);
|
||||||
|
printer->AbortPrintThread();
|
||||||
|
printer->Release();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Wait for printers
|
||||||
|
if (fNoPrinterAvailable > 0) {
|
||||||
|
acquire_sem(fNoPrinterAvailable);
|
||||||
|
delete_sem(fNoPrinterAvailable);
|
||||||
|
fNoPrinterAvailable = 0;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void PrintServerApp::RegisterPrinter(BDirectory* printer) {
|
||||||
|
BString transport, address, connection;
|
||||||
|
|
||||||
|
printer->ReadAttrString(PSRV_PRINTER_ATTR_TRANSPORT, &transport);
|
||||||
|
printer->ReadAttrString(PSRV_PRINTER_ATTR_TRANSPORT_ADDR, &address);
|
||||||
|
printer->ReadAttrString(PSRV_PRINTER_ATTR_CNX, &connection);
|
||||||
|
|
||||||
|
BAutolock lock(gLock);
|
||||||
|
if (lock.IsLocked()) {
|
||||||
|
Resource* r = fResourceManager.Allocate(transport.String(), address.String(), connection.String());
|
||||||
|
new Printer(printer, r);
|
||||||
|
if (fNumberOfPrinters == 0) acquire_sem(fNoPrinterAvailable);
|
||||||
|
fNumberOfPrinters ++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void PrintServerApp::NotifyPrinterDeletion(Resource* res) {
|
||||||
|
BAutolock lock(gLock);
|
||||||
|
if (lock.IsLocked()) {
|
||||||
|
fNumberOfPrinters --;
|
||||||
|
fResourceManager.Free(res);
|
||||||
|
if (fNumberOfPrinters == 0) release_sem(fNoPrinterAvailable);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void PrintServerApp::HandleRemovedPrinter(BMessage* msg) {
|
||||||
|
int32 opcode;
|
||||||
|
dev_t device;
|
||||||
|
ino_t node;
|
||||||
|
Printer* printer;
|
||||||
|
if (msg->FindInt32("opcode", &opcode) == B_OK && opcode == B_ENTRY_REMOVED &&
|
||||||
|
msg->FindInt32("device", &device) == B_OK &&
|
||||||
|
msg->FindInt64("node", &node) == B_OK &&
|
||||||
|
(printer = Printer::Find(device, node)) != NULL) {
|
||||||
|
if (printer == fDefaultPrinter) fDefaultPrinter = NULL;
|
||||||
|
Printer::Remove(printer);
|
||||||
|
printer->Release();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// ---------------------------------------------------------------
|
// ---------------------------------------------------------------
|
||||||
// SetupPrinterList
|
// SetupPrinterList
|
||||||
//
|
//
|
||||||
@@ -176,14 +242,14 @@ status_t PrintServerApp::SetupPrinterList()
|
|||||||
// If the entry is a directory
|
// If the entry is a directory
|
||||||
if (entry.IsDirectory()) {
|
if (entry.IsDirectory()) {
|
||||||
// Check it's Mime type for a spool director
|
// Check it's Mime type for a spool director
|
||||||
BNode node(&entry);
|
BDirectory node(&entry);
|
||||||
BNodeInfo info(&node);
|
BNodeInfo info(&node);
|
||||||
char buffer[256];
|
char buffer[256];
|
||||||
|
|
||||||
if (info.GetType(buffer) == B_OK &&
|
if (info.GetType(buffer) == B_OK &&
|
||||||
strcmp(buffer, PSRV_PRINTER_FILETYPE) == 0) {
|
strcmp(buffer, PSRV_PRINTER_FILETYPE) == 0) {
|
||||||
// Yes, it is a printer definition node
|
// Yes, it is a printer definition node
|
||||||
new Printer(&node);
|
RegisterPrinter(&node);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -234,10 +300,12 @@ PrintServerApp::MessageReceived(BMessage* msg)
|
|||||||
case B_EXECUTE_PROPERTY:
|
case B_EXECUTE_PROPERTY:
|
||||||
HandleScriptingCommand(msg);
|
HandleScriptingCommand(msg);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case B_NODE_MONITOR:
|
||||||
|
HandleRemovedPrinter(msg);
|
||||||
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
printf("PrintServerApp::MessageReceived(): ");
|
|
||||||
msg->PrintToStream();
|
|
||||||
Inherited::MessageReceived(msg);
|
Inherited::MessageReceived(msg);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -298,10 +366,12 @@ PrintServerApp::CreatePrinter(const char* printerName, const char* driverName,
|
|||||||
// call the function and check its result
|
// call the function and check its result
|
||||||
if ((*func)(printerName) == NULL) {
|
if ((*func)(printerName) == NULL) {
|
||||||
BEntry entry;
|
BEntry entry;
|
||||||
if (printer.GetEntry(&entry) == B_OK && entry.GetPath(&path) == B_OK) {
|
if (printer.GetEntry(&entry) == B_OK) {
|
||||||
// Delete the printer if function failed
|
// Delete the printer if function failed
|
||||||
::rmdir(path.Path());
|
entry.Remove();
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
RegisterPrinter(&printer);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -360,55 +430,19 @@ PrintServerApp::SelectPrinter(const char* printerName)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// ---------------------------------------------------------------
|
// ---------------------------------------------------------------
|
||||||
// HandleSpooledJob(const char* jobname, const char* filepath)
|
// HandleSpooledJobs()
|
||||||
//
|
//
|
||||||
// Handles calling the printer driver for printing a spooled job.
|
// Handles calling the printer drivers for printing a spooled job.
|
||||||
//
|
//
|
||||||
// Parameters:
|
|
||||||
// msg - A copy of the message received, will be accessible
|
|
||||||
// to the printer driver for reading job config
|
|
||||||
// details.
|
|
||||||
// Returns:
|
|
||||||
// BMessage containing new job data, or NULL pointer if not
|
|
||||||
// successfull.
|
|
||||||
// ---------------------------------------------------------------
|
// ---------------------------------------------------------------
|
||||||
status_t
|
void
|
||||||
PrintServerApp::HandleSpooledJob(const char* jobname, const char* filepath)
|
PrintServerApp::HandleSpooledJobs()
|
||||||
{
|
{
|
||||||
BFile spoolFile(filepath, B_READ_ONLY);
|
const int n = Printer::CountPrinters();
|
||||||
print_file_header header;
|
for (int i = 0; i < n; i ++) {
|
||||||
BString driverName;
|
Printer* printer = Printer::At(i);
|
||||||
BMessage settings;
|
printer->HandleSpooledJob();
|
||||||
Printer* printer;
|
|
||||||
status_t rc;
|
|
||||||
BPath path;
|
|
||||||
|
|
||||||
// Open the spool file
|
|
||||||
if ((rc=spoolFile.InitCheck()) == B_OK) {
|
|
||||||
// Read header from filestream
|
|
||||||
spoolFile.Seek(0, SEEK_SET);
|
|
||||||
spoolFile.Read(&header, sizeof(header));
|
|
||||||
|
|
||||||
// Get the printer settings
|
|
||||||
settings.Unflatten(&spoolFile);
|
|
||||||
|
|
||||||
// Get name of printer from settings
|
|
||||||
const char* printerName;
|
|
||||||
if ((rc=settings.FindString("current_printer", &printerName)) == B_OK) {
|
|
||||||
// Find printer definition for this printer
|
|
||||||
if ((printer=Printer::Find(printerName)) != NULL) {
|
|
||||||
// and tell the printer to print the spooled job
|
|
||||||
printer->PrintSpooledJob(&spoolFile, settings);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Remove spool file if printing was successfull.
|
|
||||||
if (rc == B_OK) {
|
|
||||||
::unlink(filepath);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return rc;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// ---------------------------------------------------------------
|
// ---------------------------------------------------------------
|
||||||
|
|||||||
@@ -6,6 +6,9 @@
|
|||||||
// The print_server manages the communication between applications and the
|
// The print_server manages the communication between applications and the
|
||||||
// printer and transport drivers.
|
// printer and transport drivers.
|
||||||
//
|
//
|
||||||
|
// Authors
|
||||||
|
// Ithamar R. Adema
|
||||||
|
// Michael Pfeiffer
|
||||||
//
|
//
|
||||||
// This application and all source files used in its construction, except
|
// This application and all source files used in its construction, except
|
||||||
// where noted, are licensed under the MIT License, and have been written
|
// where noted, are licensed under the MIT License, and have been written
|
||||||
@@ -35,12 +38,18 @@
|
|||||||
#ifndef PRINTSERVERAPP_H
|
#ifndef PRINTSERVERAPP_H
|
||||||
#define PRINTSERVERAPP_H
|
#define PRINTSERVERAPP_H
|
||||||
|
|
||||||
|
#include "ResourceManager.h"
|
||||||
|
|
||||||
class PrintServerApp;
|
class PrintServerApp;
|
||||||
|
|
||||||
#include <Application.h>
|
#include <Application.h>
|
||||||
#include <Bitmap.h>
|
#include <Bitmap.h>
|
||||||
|
#include <OS.h>
|
||||||
#include <String.h>
|
#include <String.h>
|
||||||
|
|
||||||
|
// global BLocker for synchronisation
|
||||||
|
extern BLocker* gLock;
|
||||||
|
|
||||||
/*****************************************************************************/
|
/*****************************************************************************/
|
||||||
// PrintServerApp
|
// PrintServerApp
|
||||||
//
|
//
|
||||||
@@ -52,8 +61,10 @@ class PrintServerApp : public BApplication
|
|||||||
typedef BApplication Inherited;
|
typedef BApplication Inherited;
|
||||||
public:
|
public:
|
||||||
PrintServerApp(status_t* err);
|
PrintServerApp(status_t* err);
|
||||||
|
|
||||||
bool QuitRequested();
|
bool QuitRequested();
|
||||||
void MessageReceived(BMessage* msg);
|
void MessageReceived(BMessage* msg);
|
||||||
|
void NotifyPrinterDeletion(Resource* res);
|
||||||
|
|
||||||
// Scripting support, see PrintServerApp.Scripting.cpp
|
// Scripting support, see PrintServerApp.Scripting.cpp
|
||||||
status_t GetSupportedSuites(BMessage* msg);
|
status_t GetSupportedSuites(BMessage* msg);
|
||||||
@@ -64,12 +75,15 @@ public:
|
|||||||
private:
|
private:
|
||||||
status_t SetupPrinterList();
|
status_t SetupPrinterList();
|
||||||
|
|
||||||
status_t HandleSpooledJob(const char* jobname, const char* filepath);
|
void HandleSpooledJobs();
|
||||||
|
|
||||||
status_t SelectPrinter(const char* printerName);
|
status_t SelectPrinter(const char* printerName);
|
||||||
status_t CreatePrinter( const char* printerName, const char* driverName,
|
status_t CreatePrinter( const char* printerName, const char* driverName,
|
||||||
const char* connection, const char* transportName,
|
const char* connection, const char* transportName,
|
||||||
const char* transportPath);
|
const char* transportPath);
|
||||||
|
|
||||||
|
void RegisterPrinter(BDirectory* node);
|
||||||
|
void HandleRemovedPrinter(BMessage* msg);
|
||||||
|
|
||||||
status_t StoreDefaultPrinter();
|
status_t StoreDefaultPrinter();
|
||||||
status_t RetrieveDefaultPrinter();
|
status_t RetrieveDefaultPrinter();
|
||||||
@@ -77,14 +91,18 @@ private:
|
|||||||
status_t FindPrinterNode(const char* name, BNode& node);
|
status_t FindPrinterNode(const char* name, BNode& node);
|
||||||
status_t FindPrinterDriver(const char* name, BPath& outPath);
|
status_t FindPrinterDriver(const char* name, BPath& outPath);
|
||||||
|
|
||||||
|
ResourceManager fResourceManager;
|
||||||
Printer* fDefaultPrinter;
|
Printer* fDefaultPrinter;
|
||||||
BBitmap fSelectedIconMini;
|
BBitmap fSelectedIconMini;
|
||||||
BBitmap fSelectedIconLarge;
|
BBitmap fSelectedIconLarge;
|
||||||
|
int fNumberOfPrinters;
|
||||||
|
sem_id fNoPrinterAvailable;
|
||||||
|
|
||||||
// "Classic" BeOS R5 support, see PrintServerApp.R5.cpp
|
// "Classic" BeOS R5 support, see PrintServerApp.R5.cpp
|
||||||
static status_t async_thread(void* data);
|
static status_t async_thread(void* data);
|
||||||
void AsyncHandleMessage(BMessage* msg);
|
void AsyncHandleMessage(BMessage* msg);
|
||||||
void Handle_BeOSR5_Message(BMessage* msg);
|
void Handle_BeOSR5_Message(BMessage* msg);
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -1,3 +1,39 @@
|
|||||||
|
/*****************************************************************************/
|
||||||
|
// print_server Background Application.
|
||||||
|
//
|
||||||
|
// Version: 1.0.0d1
|
||||||
|
//
|
||||||
|
// The print_server manages the communication between applications and the
|
||||||
|
// printer and transport drivers.
|
||||||
|
//
|
||||||
|
// Author
|
||||||
|
// Ithamar R. Adema
|
||||||
|
//
|
||||||
|
// This application and all source files used in its construction, except
|
||||||
|
// where noted, are licensed under the MIT License, and have been written
|
||||||
|
// and are:
|
||||||
|
//
|
||||||
|
// Copyright (c) 2001 OpenBeOS Project
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||||
|
// copy of this software and associated documentation files (the "Software"),
|
||||||
|
// to deal in the Software without restriction, including without limitation
|
||||||
|
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||||
|
// and/or sell copies of the Software, and to permit persons to whom the
|
||||||
|
// Software is furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included
|
||||||
|
// in all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||||
|
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||||
|
// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||||
|
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||||
|
// DEALINGS IN THE SOFTWARE.
|
||||||
|
/*****************************************************************************/
|
||||||
|
|
||||||
#include "Printer.h"
|
#include "Printer.h"
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
+151
-47
@@ -6,18 +6,15 @@
|
|||||||
// The print_server manages the communication between applications and the
|
// The print_server manages the communication between applications and the
|
||||||
// printer and transport drivers.
|
// printer and transport drivers.
|
||||||
//
|
//
|
||||||
//
|
// Authors
|
||||||
//
|
// Ithamar R. Adema
|
||||||
// TODO:
|
// Michael Pfeiffer
|
||||||
// Handle spooled jobs at startup
|
|
||||||
// Handle printer status (asked to print a spooled job but printer busy)
|
|
||||||
//
|
|
||||||
//
|
//
|
||||||
// This application and all source files used in its construction, except
|
// This application and all source files used in its construction, except
|
||||||
// where noted, are licensed under the MIT License, and have been written
|
// where noted, are licensed under the MIT License, and have been written
|
||||||
// and are:
|
// and are:
|
||||||
//
|
//
|
||||||
// Copyright (c) 2001 OpenBeOS Project
|
// Copyright (c) 2001,2002 OpenBeOS Project
|
||||||
//
|
//
|
||||||
// Permission is hereby granted, free of charge, to any person obtaining a
|
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||||
// copy of this software and associated documentation files (the "Software"),
|
// copy of this software and associated documentation files (the "Software"),
|
||||||
@@ -42,13 +39,21 @@
|
|||||||
|
|
||||||
#include "pr_server.h"
|
#include "pr_server.h"
|
||||||
#include "BeUtils.h"
|
#include "BeUtils.h"
|
||||||
|
#include "PrintServerApp.h"
|
||||||
|
|
||||||
|
// posix
|
||||||
|
#include <limits.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
// BeOS API
|
// BeOS API
|
||||||
#include <Application.h>
|
#include <Application.h>
|
||||||
|
#include <Autolock.h>
|
||||||
#include <Message.h>
|
#include <Message.h>
|
||||||
|
#include <NodeMonitor.h>
|
||||||
#include <String.h>
|
#include <String.h>
|
||||||
#include <File.h>
|
#include <StorageKit.h>
|
||||||
#include <Path.h>
|
#include <SupportDefs.h>
|
||||||
|
|
||||||
// ---------------------------------------------------------------
|
// ---------------------------------------------------------------
|
||||||
typedef BMessage* (*config_func_t)(BNode*, const BMessage*);
|
typedef BMessage* (*config_func_t)(BNode*, const BMessage*);
|
||||||
@@ -84,9 +89,18 @@ Printer* Printer::Find(const BString& name)
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
int32 Printer::CountPrinters()
|
Printer* Printer::Find(dev_t dev, ino_t node)
|
||||||
{
|
{
|
||||||
return sPrinters.CountItems();
|
// Look in list to find printer definition
|
||||||
|
for (int32 idx=0; idx < sPrinters.CountItems(); idx++) {
|
||||||
|
Printer* printer = sPrinters.ItemAt(idx);
|
||||||
|
node_ref ref;
|
||||||
|
printer->fNode.GetNodeRef(&ref);
|
||||||
|
if (ref.device == dev && ref.node == node) return printer;
|
||||||
|
}
|
||||||
|
|
||||||
|
// None found, so return NULL
|
||||||
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
Printer* Printer::At(int32 idx)
|
Printer* Printer::At(int32 idx)
|
||||||
@@ -94,6 +108,15 @@ Printer* Printer::At(int32 idx)
|
|||||||
return sPrinters.ItemAt(idx);
|
return sPrinters.ItemAt(idx);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Printer::Remove(Printer* printer) {
|
||||||
|
sPrinters.RemoveItem(printer);
|
||||||
|
}
|
||||||
|
|
||||||
|
int32 Printer::CountPrinters()
|
||||||
|
{
|
||||||
|
return sPrinters.CountItems();
|
||||||
|
}
|
||||||
|
|
||||||
// ---------------------------------------------------------------
|
// ---------------------------------------------------------------
|
||||||
// Printer [constructor]
|
// Printer [constructor]
|
||||||
//
|
//
|
||||||
@@ -106,15 +129,22 @@ Printer* Printer::At(int32 idx)
|
|||||||
// Returns:
|
// Returns:
|
||||||
// none.
|
// none.
|
||||||
// ---------------------------------------------------------------
|
// ---------------------------------------------------------------
|
||||||
Printer::Printer(const BNode* node)
|
Printer::Printer(const BDirectory* node, Resource* res)
|
||||||
: Inherited(B_EMPTY_STRING),
|
: Inherited(B_EMPTY_STRING),
|
||||||
|
fFolder(*node),
|
||||||
|
fResource(res),
|
||||||
fNode(*node),
|
fNode(*node),
|
||||||
fRefCount(1)
|
fSinglePrintThread(true),
|
||||||
|
fJob(NULL),
|
||||||
|
fProcessing(0),
|
||||||
|
fAbort(false)
|
||||||
{
|
{
|
||||||
// Set our name to the name of the passed node
|
// Set our name to the name of the passed node
|
||||||
BString name;
|
BString name;
|
||||||
fNode.ReadAttrString(PSRV_PRINTER_ATTR_PRT_NAME, &name);
|
fNode.ReadAttrString(PSRV_PRINTER_ATTR_PRT_NAME, &name);
|
||||||
SetName(name.String());
|
SetName(name.String());
|
||||||
|
|
||||||
|
if (name == "Preview") fSinglePrintThread = false;
|
||||||
|
|
||||||
// Add us to the global list of known printer definitions
|
// Add us to the global list of known printer definitions
|
||||||
sPrinters.AddItem(this);
|
sPrinters.AddItem(this);
|
||||||
@@ -123,19 +153,7 @@ Printer::Printer(const BNode* node)
|
|||||||
|
|
||||||
Printer::~Printer()
|
Printer::~Printer()
|
||||||
{
|
{
|
||||||
sPrinters.RemoveItem(this);
|
((PrintServerApp*)be_app)->NotifyPrinterDeletion(fResource);
|
||||||
be_app->RemoveHandler(this);
|
|
||||||
}
|
|
||||||
|
|
||||||
void Printer::Acquire()
|
|
||||||
{
|
|
||||||
fRefCount ++;
|
|
||||||
}
|
|
||||||
|
|
||||||
void Printer::Release()
|
|
||||||
{
|
|
||||||
fRefCount --;
|
|
||||||
if (fRefCount == 0) delete this;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
status_t Printer::Remove()
|
status_t Printer::Remove()
|
||||||
@@ -144,6 +162,8 @@ status_t Printer::Remove()
|
|||||||
BPath path;
|
BPath path;
|
||||||
|
|
||||||
if ((rc=::find_directory(B_USER_PRINTERS_DIRECTORY, &path)) == B_OK) {
|
if ((rc=::find_directory(B_USER_PRINTERS_DIRECTORY, &path)) == B_OK) {
|
||||||
|
sPrinters.RemoveItem(this);
|
||||||
|
be_app->RemoveHandler(this);
|
||||||
path.Append(Name());
|
path.Append(Name());
|
||||||
rc = rmdir(path.Path());
|
rc = rmdir(path.Path());
|
||||||
}
|
}
|
||||||
@@ -242,29 +262,11 @@ status_t Printer::ConfigureJob(BMessage& settings)
|
|||||||
if ((rc=get_image_symbol(id, "config_job", B_SYMBOL_TYPE_TEXT, (void**)&func)) == B_OK) {
|
if ((rc=get_image_symbol(id, "config_job", B_SYMBOL_TYPE_TEXT, (void**)&func)) == B_OK) {
|
||||||
// call the function and check its result
|
// call the function and check its result
|
||||||
BMessage* new_settings = (*func)(&fNode, &settings);
|
BMessage* new_settings = (*func)(&fNode, &settings);
|
||||||
if (new_settings != NULL && new_settings->what != 'baad')
|
if ((new_settings != NULL) && (new_settings->what != 'baad'))
|
||||||
settings = *new_settings;
|
settings = *new_settings;
|
||||||
}
|
else
|
||||||
|
|
||||||
::unload_add_on(id);
|
|
||||||
}
|
|
||||||
|
|
||||||
return rc;
|
|
||||||
}
|
|
||||||
|
|
||||||
status_t Printer::PrintSpooledJob(BFile* spoolFile, const BMessage& settings)
|
|
||||||
{
|
|
||||||
take_job_func_t func;
|
|
||||||
image_id id;
|
|
||||||
status_t rc;
|
|
||||||
|
|
||||||
if ((rc=LoadPrinterAddon(id)) == B_OK) {
|
|
||||||
// Addon was loaded, so try and get the take_job symbol
|
|
||||||
if ((rc=get_image_symbol(id, "take_job", B_SYMBOL_TYPE_TEXT, (void**)&func)) == B_OK) {
|
|
||||||
// call the function and check its result
|
|
||||||
BMessage* result = (*func)(spoolFile, &fNode, &settings);
|
|
||||||
if (result == NULL || result->what == 'baad')
|
|
||||||
rc = B_ERROR;
|
rc = B_ERROR;
|
||||||
|
delete new_settings;
|
||||||
}
|
}
|
||||||
|
|
||||||
::unload_add_on(id);
|
::unload_add_on(id);
|
||||||
@@ -273,6 +275,23 @@ status_t Printer::PrintSpooledJob(BFile* spoolFile, const BMessage& settings)
|
|||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// ---------------------------------------------------------------
|
||||||
|
// HandleSpooledJobs
|
||||||
|
//
|
||||||
|
// Print spooled jobs in a new thread.
|
||||||
|
// ---------------------------------------------------------------
|
||||||
|
void Printer::HandleSpooledJob() {
|
||||||
|
BAutolock lock(gLock);
|
||||||
|
if (lock.IsLocked() && (!fSinglePrintThread || fProcessing == 0) && FindSpooledJob()) {
|
||||||
|
StartPrintThread();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Printer::AbortPrintThread() {
|
||||||
|
fAbort = true;
|
||||||
|
}
|
||||||
|
|
||||||
// ---------------------------------------------------------------
|
// ---------------------------------------------------------------
|
||||||
// LoadPrinterAddon
|
// LoadPrinterAddon
|
||||||
//
|
//
|
||||||
@@ -310,6 +329,10 @@ status_t Printer::LoadPrinterAddon(image_id& id)
|
|||||||
|
|
||||||
void Printer::MessageReceived(BMessage* msg)
|
void Printer::MessageReceived(BMessage* msg)
|
||||||
{
|
{
|
||||||
|
printf("Printer::MessageReceived(): ");
|
||||||
|
msg->PrintToStream();
|
||||||
|
|
||||||
|
|
||||||
switch(msg->what) {
|
switch(msg->what) {
|
||||||
case B_GET_PROPERTY:
|
case B_GET_PROPERTY:
|
||||||
case B_SET_PROPERTY:
|
case B_SET_PROPERTY:
|
||||||
@@ -324,3 +347,84 @@ void Printer::MessageReceived(BMessage* msg)
|
|||||||
Inherited::MessageReceived(msg);
|
Inherited::MessageReceived(msg);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool Printer::FindSpooledJob() {
|
||||||
|
fJob = fFolder.GetNextJob();
|
||||||
|
if (fJob) fJob->SetPrinter(this);
|
||||||
|
return fJob;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Printer::CloseJob() {
|
||||||
|
fJob->Release();
|
||||||
|
}
|
||||||
|
|
||||||
|
status_t Printer::PrintSpooledJob(BFile* spoolFile, const BMessage& settings)
|
||||||
|
{
|
||||||
|
take_job_func_t func;
|
||||||
|
image_id id;
|
||||||
|
status_t rc;
|
||||||
|
|
||||||
|
if ((rc=LoadPrinterAddon(id)) == B_OK) {
|
||||||
|
// Addon was loaded, so try and get the take_job symbol
|
||||||
|
if ((rc=get_image_symbol(id, "take_job", B_SYMBOL_TYPE_TEXT, (void**)&func)) == B_OK) {
|
||||||
|
// call the function and check its result
|
||||||
|
BMessage* result = (*func)(spoolFile, &fNode, &settings);
|
||||||
|
if (result == NULL || result->what == 'baad')
|
||||||
|
rc = B_ERROR;
|
||||||
|
}
|
||||||
|
|
||||||
|
::unload_add_on(id);
|
||||||
|
}
|
||||||
|
|
||||||
|
return rc;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Printer::PrintThread(Job* job) {
|
||||||
|
fResource->Lock();
|
||||||
|
if (!fAbort) {
|
||||||
|
BFile jobFile(&job->EntryRef(), B_READ_ONLY);
|
||||||
|
print_file_header header;
|
||||||
|
BMessage settings;
|
||||||
|
|
||||||
|
// Read header from filestream
|
||||||
|
jobFile.Seek(0, SEEK_SET);
|
||||||
|
jobFile.Read(&header, sizeof(header));
|
||||||
|
|
||||||
|
// Get the printer settings
|
||||||
|
settings.Unflatten(&jobFile);
|
||||||
|
|
||||||
|
// and tell the printer to print the spooled job
|
||||||
|
if (PrintSpooledJob(&jobFile, settings) == B_OK) {
|
||||||
|
// Remove spool file if printing was successfull.
|
||||||
|
job->Remove();
|
||||||
|
} else {
|
||||||
|
job->SetStatus(kFailed);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
job->SetStatus(kFailed);
|
||||||
|
}
|
||||||
|
fResource->Unlock();
|
||||||
|
job->Release();
|
||||||
|
atomic_add(&fProcessing, -1);
|
||||||
|
Release();
|
||||||
|
be_app_messenger.SendMessage(PSRV_PRINT_SPOOLED_JOB);
|
||||||
|
}
|
||||||
|
|
||||||
|
status_t Printer::print_thread(void* data) {
|
||||||
|
Job* job = static_cast<Job*>(data);
|
||||||
|
job->GetPrinter()->PrintThread(job);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
status_t Printer::StartPrintThread() {
|
||||||
|
Acquire();
|
||||||
|
thread_id tid = spawn_thread(print_thread, "print", B_NORMAL_PRIORITY, (void*)fJob);
|
||||||
|
if (tid > 0) {
|
||||||
|
fJob->SetStatus(kProcessing);
|
||||||
|
atomic_add(&fProcessing, 1);
|
||||||
|
resume_thread(tid);
|
||||||
|
} else {
|
||||||
|
CloseJob(); Release();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|||||||
+31
-16
@@ -5,13 +5,10 @@
|
|||||||
//
|
//
|
||||||
// The print_server manages the communication between applications and the
|
// The print_server manages the communication between applications and the
|
||||||
// printer and transport drivers.
|
// printer and transport drivers.
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
// TODO:
|
|
||||||
// Handle spooled jobs at startup
|
|
||||||
// Handle printer status (asked to print a spooled job but printer busy)
|
|
||||||
//
|
//
|
||||||
|
// Authors
|
||||||
|
// Ithamar R. Adema
|
||||||
|
// Michael Pfeiffer
|
||||||
//
|
//
|
||||||
// This application and all source files used in its construction, except
|
// This application and all source files used in its construction, except
|
||||||
// where noted, are licensed under the MIT License, and have been written
|
// where noted, are licensed under the MIT License, and have been written
|
||||||
@@ -43,11 +40,17 @@
|
|||||||
|
|
||||||
class Printer;
|
class Printer;
|
||||||
|
|
||||||
|
#include "BeUtils.h"
|
||||||
|
#include "ResourceManager.h"
|
||||||
|
#include "Jobs.h"
|
||||||
|
|
||||||
// BeOS API
|
// BeOS API
|
||||||
|
#include <Directory.h>
|
||||||
#include <Handler.h>
|
#include <Handler.h>
|
||||||
#include <String.h>
|
|
||||||
#include <image.h>
|
#include <image.h>
|
||||||
#include <Node.h>
|
#include <Locker.h>
|
||||||
|
#include <PrintJob.h>
|
||||||
|
#include <String.h>
|
||||||
|
|
||||||
// OpenTracker shared sources
|
// OpenTracker shared sources
|
||||||
#include "ObjectList.h"
|
#include "ObjectList.h"
|
||||||
@@ -58,27 +61,27 @@ class Printer;
|
|||||||
// This class represents one printer definition. It is manages all actions &
|
// This class represents one printer definition. It is manages all actions &
|
||||||
// data related to that printer.
|
// data related to that printer.
|
||||||
/*****************************************************************************/
|
/*****************************************************************************/
|
||||||
class Printer : public BHandler
|
class Printer : public BHandler, public Object
|
||||||
{
|
{
|
||||||
typedef BHandler Inherited;
|
typedef BHandler Inherited;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
Printer(const BNode* node);
|
Printer(const BDirectory* node, Resource* res);
|
||||||
~Printer();
|
~Printer();
|
||||||
|
|
||||||
void Acquire();
|
|
||||||
void Release();
|
|
||||||
|
|
||||||
// Static helper functions
|
// Static helper functions
|
||||||
static Printer* Find(const BString& name);
|
static Printer* Find(const BString& name);
|
||||||
|
static Printer* Find(dev_t device, ino_t node);
|
||||||
static Printer* At(int32 idx);
|
static Printer* At(int32 idx);
|
||||||
|
static void Remove(Printer* printer);
|
||||||
static int32 CountPrinters();
|
static int32 CountPrinters();
|
||||||
|
|
||||||
status_t Remove();
|
status_t Remove();
|
||||||
status_t ConfigurePrinter();
|
status_t ConfigurePrinter();
|
||||||
status_t ConfigureJob(BMessage& ioSettings);
|
status_t ConfigureJob(BMessage& ioSettings);
|
||||||
status_t ConfigurePage(BMessage& ioSettings);
|
status_t ConfigurePage(BMessage& ioSettings);
|
||||||
status_t PrintSpooledJob(BFile* spoolFile, const BMessage& settings);
|
void HandleSpooledJob();
|
||||||
|
void AbortPrintThread();
|
||||||
|
|
||||||
void MessageReceived(BMessage* msg);
|
void MessageReceived(BMessage* msg);
|
||||||
|
|
||||||
@@ -90,10 +93,22 @@ public:
|
|||||||
private:
|
private:
|
||||||
status_t LoadPrinterAddon(image_id& id);
|
status_t LoadPrinterAddon(image_id& id);
|
||||||
|
|
||||||
BNode fNode;
|
Folder fFolder;
|
||||||
int32 fRefCount;
|
Resource* fResource;
|
||||||
|
BDirectory fNode;
|
||||||
|
bool fSinglePrintThread;
|
||||||
|
Job* fJob;
|
||||||
|
volatile vint32 fProcessing;
|
||||||
|
bool fAbort;
|
||||||
|
|
||||||
static BObjectList<Printer> sPrinters;
|
static BObjectList<Printer> sPrinters;
|
||||||
|
|
||||||
|
bool FindSpooledJob();
|
||||||
|
void CloseJob();
|
||||||
|
status_t PrintSpooledJob(BFile* spoolFile, const BMessage& settings);
|
||||||
|
void PrintThread(Job* job);
|
||||||
|
static status_t print_thread(void* data);
|
||||||
|
status_t StartPrintThread();
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@@ -0,0 +1,104 @@
|
|||||||
|
/*****************************************************************************/
|
||||||
|
// ResourceManager
|
||||||
|
//
|
||||||
|
// Author
|
||||||
|
// Michael Pfeiffer
|
||||||
|
//
|
||||||
|
// This application and all source files used in its construction, except
|
||||||
|
// where noted, are licensed under the MIT License, and have been written
|
||||||
|
// and are:
|
||||||
|
//
|
||||||
|
// Copyright (c) 2002 OpenBeOS Project
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||||
|
// copy of this software and associated documentation files (the "Software"),
|
||||||
|
// to deal in the Software without restriction, including without limitation
|
||||||
|
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||||
|
// and/or sell copies of the Software, and to permit persons to whom the
|
||||||
|
// Software is furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included
|
||||||
|
// in all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||||
|
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||||
|
// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||||
|
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||||
|
// DEALINGS IN THE SOFTWARE.
|
||||||
|
/*****************************************************************************/
|
||||||
|
|
||||||
|
#include "ResourceManager.h"
|
||||||
|
|
||||||
|
#include <Debug.h>
|
||||||
|
#include <Autolock.h>
|
||||||
|
|
||||||
|
Resource::Resource(const char* transport, const char* address, const char* connection)
|
||||||
|
: fTransport(transport)
|
||||||
|
, fTransportAddress(address)
|
||||||
|
, fConnection(connection)
|
||||||
|
, fResourceAvailable(0)
|
||||||
|
|
||||||
|
{
|
||||||
|
if (NeedsLocking()) {
|
||||||
|
fResourceAvailable = create_sem(1, "resource");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Resource::~Resource() {
|
||||||
|
if (fResourceAvailable > 0) delete_sem(fResourceAvailable);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Resource::NeedsLocking() {
|
||||||
|
return !(fTransport == "Print to File" || fTransport == "NONE");
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Resource::Equals(const char* transport, const char* address, const char* connection) {
|
||||||
|
return fTransport == transport &&
|
||||||
|
fTransportAddress == address &&
|
||||||
|
fConnection == connection;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Resource::Lock() {
|
||||||
|
if (fResourceAvailable > 0) {
|
||||||
|
return acquire_sem(fResourceAvailable) == B_NO_ERROR;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Resource::Unlock() {
|
||||||
|
if (fResourceAvailable > 0) {
|
||||||
|
release_sem(fResourceAvailable);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ResourceManager::~ResourceManager() {
|
||||||
|
ASSERT(fResources.CountItems() == 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
Resource* ResourceManager::Find(const char* transport, const char* address, const char* connection) {
|
||||||
|
for (int i = 0; i < fResources.CountItems(); i ++) {
|
||||||
|
Resource* r = fResources.ItemAt(i);
|
||||||
|
if (r->Equals(transport, address, connection)) return r;
|
||||||
|
}
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
Resource* ResourceManager::Allocate(const char* transport, const char* address, const char* connection) {
|
||||||
|
Resource* r = Find(transport, address, connection);
|
||||||
|
if (r == NULL) {
|
||||||
|
r = new Resource(transport, address, connection);
|
||||||
|
fResources.AddItem(r);
|
||||||
|
} else {
|
||||||
|
r->Acquire();
|
||||||
|
}
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void ResourceManager::Free(Resource* r) {
|
||||||
|
if (r->Release()) {
|
||||||
|
fResources.RemoveItem(r);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,78 @@
|
|||||||
|
/*****************************************************************************/
|
||||||
|
// ResourceManager
|
||||||
|
//
|
||||||
|
// Author
|
||||||
|
// Michael Pfeiffer
|
||||||
|
//
|
||||||
|
// This application and all source files used in its construction, except
|
||||||
|
// where noted, are licensed under the MIT License, and have been written
|
||||||
|
// and are:
|
||||||
|
//
|
||||||
|
// Copyright (c) 2002 OpenBeOS Project
|
||||||
|
//
|
||||||
|
// Permission is hereby granted, free of charge, to any person obtaining a
|
||||||
|
// copy of this software and associated documentation files (the "Software"),
|
||||||
|
// to deal in the Software without restriction, including without limitation
|
||||||
|
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||||
|
// and/or sell copies of the Software, and to permit persons to whom the
|
||||||
|
// Software is furnished to do so, subject to the following conditions:
|
||||||
|
//
|
||||||
|
// The above copyright notice and this permission notice shall be included
|
||||||
|
// in all copies or substantial portions of the Software.
|
||||||
|
//
|
||||||
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||||
|
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||||
|
// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||||
|
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||||
|
// DEALINGS IN THE SOFTWARE.
|
||||||
|
/*****************************************************************************/
|
||||||
|
|
||||||
|
|
||||||
|
#ifndef RESOURCE_MANAGER_H
|
||||||
|
#define RESOURCE_MANAGER_H
|
||||||
|
|
||||||
|
#include "ObjectList.h"
|
||||||
|
|
||||||
|
#include <Locker.h>
|
||||||
|
#include <String.h>
|
||||||
|
|
||||||
|
#include "BeUtils.h"
|
||||||
|
|
||||||
|
class Resource : public Object {
|
||||||
|
private:
|
||||||
|
BString fTransport;
|
||||||
|
BString fTransportAddress;
|
||||||
|
BString fConnection;
|
||||||
|
sem_id fResourceAvailable;
|
||||||
|
|
||||||
|
bool NeedsLocking();
|
||||||
|
|
||||||
|
|
||||||
|
public:
|
||||||
|
Resource(const char* transport, const char* address, const char* connection);
|
||||||
|
~Resource();
|
||||||
|
|
||||||
|
bool Equals(const char* transport, const char* address, const char* connection);
|
||||||
|
|
||||||
|
const BString& Transport() const { return fTransport; }
|
||||||
|
|
||||||
|
bool Lock();
|
||||||
|
void Unlock();
|
||||||
|
};
|
||||||
|
|
||||||
|
class ResourceManager {
|
||||||
|
private:
|
||||||
|
BObjectList<Resource> fResources;
|
||||||
|
|
||||||
|
Resource* Find(const char* transport, const char* address, const char* connection);
|
||||||
|
|
||||||
|
public:
|
||||||
|
~ResourceManager();
|
||||||
|
|
||||||
|
Resource* Allocate(const char* transport, const char* address, const char* connection);
|
||||||
|
void Free(Resource* r);
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
Reference in New Issue
Block a user