162cb58a8SIthamar R. Adema /* 262cb58a8SIthamar R. Adema * Copyright 2008, Haiku. All rights reserved. 362cb58a8SIthamar R. Adema * Distributed under the terms of the MIT License. 462cb58a8SIthamar R. Adema * 562cb58a8SIthamar R. Adema * Authors: 662cb58a8SIthamar R. Adema * Ithamar R. Adema 762cb58a8SIthamar R. Adema */ 862cb58a8SIthamar R. Adema 962cb58a8SIthamar R. Adema #include "Transport.h" 1062cb58a8SIthamar R. Adema 1162cb58a8SIthamar R. Adema // BeOS API 1262cb58a8SIthamar R. Adema #include <PrintTransportAddOn.h> 1362cb58a8SIthamar R. Adema #include <Application.h> 1462cb58a8SIthamar R. Adema #include <image.h> 1562cb58a8SIthamar R. Adema #include <Entry.h> 1662cb58a8SIthamar R. Adema 179abbe87fSMichael Pfeiffer 1862cb58a8SIthamar R. Adema BObjectList<Transport> Transport::sTransports; 1962cb58a8SIthamar R. Adema 209abbe87fSMichael Pfeiffer 2162cb58a8SIthamar R. Adema // --------------------------------------------------------------- 2262cb58a8SIthamar R. Adema // Find [static] 2362cb58a8SIthamar R. Adema // 2462cb58a8SIthamar R. Adema // Searches the static object list for a transport object with the 2562cb58a8SIthamar R. Adema // specified name. 2662cb58a8SIthamar R. Adema // 2762cb58a8SIthamar R. Adema // Parameters: 2862cb58a8SIthamar R. Adema // name - Printer definition name we're looking for. 2962cb58a8SIthamar R. Adema // 3062cb58a8SIthamar R. Adema // Returns: 3162cb58a8SIthamar R. Adema // Pointer to Transport object, or NULL if not found. 3262cb58a8SIthamar R. Adema // --------------------------------------------------------------- 339abbe87fSMichael Pfeiffer Transport* 349abbe87fSMichael Pfeiffer Transport::Find(const BString& name) 3562cb58a8SIthamar R. Adema { 3662cb58a8SIthamar R. Adema // Look in list to find printer definition 37*1797be0dSStefano Ceccherini for (int32 index = 0; index < sTransports.CountItems(); index++) { 38*1797be0dSStefano Ceccherini if (name == sTransports.ItemAt(index)->Name()) 39*1797be0dSStefano Ceccherini return sTransports.ItemAt(index); 4062cb58a8SIthamar R. Adema } 4162cb58a8SIthamar R. Adema 4262cb58a8SIthamar R. Adema // None found, so return NULL 4362cb58a8SIthamar R. Adema return NULL; 4462cb58a8SIthamar R. Adema } 4562cb58a8SIthamar R. Adema 469abbe87fSMichael Pfeiffer 479abbe87fSMichael Pfeiffer Transport* 48*1797be0dSStefano Ceccherini Transport::At(int32 index) 4962cb58a8SIthamar R. Adema { 50*1797be0dSStefano Ceccherini return sTransports.ItemAt(index); 5162cb58a8SIthamar R. Adema } 5262cb58a8SIthamar R. Adema 539abbe87fSMichael Pfeiffer 549abbe87fSMichael Pfeiffer void 559abbe87fSMichael Pfeiffer Transport::Remove(Transport* transport) 5662cb58a8SIthamar R. Adema { 5762cb58a8SIthamar R. Adema sTransports.RemoveItem(transport); 5862cb58a8SIthamar R. Adema } 5962cb58a8SIthamar R. Adema 609abbe87fSMichael Pfeiffer 619abbe87fSMichael Pfeiffer int32 629abbe87fSMichael Pfeiffer Transport::CountTransports() 6362cb58a8SIthamar R. Adema { 6462cb58a8SIthamar R. Adema return sTransports.CountItems(); 6562cb58a8SIthamar R. Adema } 6662cb58a8SIthamar R. Adema 679abbe87fSMichael Pfeiffer 689abbe87fSMichael Pfeiffer status_t 699abbe87fSMichael Pfeiffer Transport::Scan(directory_which which) 7062cb58a8SIthamar R. Adema { 71*1797be0dSStefano Ceccherini status_t result; 7262cb58a8SIthamar R. Adema BPath path; 7362cb58a8SIthamar R. Adema 7462cb58a8SIthamar R. Adema // Try to find specified transport addon directory 75*1797be0dSStefano Ceccherini if ((result = find_directory(which, &path)) != B_OK) 76*1797be0dSStefano Ceccherini return result; 7762cb58a8SIthamar R. Adema 78*1797be0dSStefano Ceccherini if ((result = path.Append("Print/transport")) != B_OK) 79*1797be0dSStefano Ceccherini return result; 8062cb58a8SIthamar R. Adema 81*1797be0dSStefano Ceccherini BDirectory dir; 82*1797be0dSStefano Ceccherini if ((result = dir.SetTo(path.Path())) != B_OK) 83*1797be0dSStefano Ceccherini return result; 8462cb58a8SIthamar R. Adema 8562cb58a8SIthamar R. Adema // Walk over all entries in directory 8662cb58a8SIthamar R. Adema BEntry entry; 8762cb58a8SIthamar R. Adema while(dir.GetNextEntry(&entry) == B_OK) { 8862cb58a8SIthamar R. Adema if (!entry.IsFile()) 8962cb58a8SIthamar R. Adema continue; 9062cb58a8SIthamar R. Adema 9162cb58a8SIthamar R. Adema if (entry.GetPath(&path) != B_OK) 9262cb58a8SIthamar R. Adema continue; 9362cb58a8SIthamar R. Adema 9462cb58a8SIthamar R. Adema // If we have loaded the transport from a previous scanned directory, 9562cb58a8SIthamar R. Adema // ignore this one. 9662cb58a8SIthamar R. Adema if (Transport::Find(path.Leaf()) != NULL) 9762cb58a8SIthamar R. Adema continue; 9862cb58a8SIthamar R. Adema 9962cb58a8SIthamar R. Adema be_app->AddHandler(new Transport(path)); 10062cb58a8SIthamar R. Adema } 10162cb58a8SIthamar R. Adema 10262cb58a8SIthamar R. Adema return B_OK; 10362cb58a8SIthamar R. Adema } 10462cb58a8SIthamar R. Adema 1059abbe87fSMichael Pfeiffer 10662cb58a8SIthamar R. Adema // --------------------------------------------------------------- 10762cb58a8SIthamar R. Adema // Transport [constructor] 10862cb58a8SIthamar R. Adema // 10962cb58a8SIthamar R. Adema // Initializes the transport object with data read from the 11062cb58a8SIthamar R. Adema // attributes attached to the printer definition node. 11162cb58a8SIthamar R. Adema // 11262cb58a8SIthamar R. Adema // Parameters: 11362cb58a8SIthamar R. Adema // node - Printer definition node for this printer. 11462cb58a8SIthamar R. Adema // 11562cb58a8SIthamar R. Adema // Returns: 11662cb58a8SIthamar R. Adema // none. 11762cb58a8SIthamar R. Adema // --------------------------------------------------------------- 11862cb58a8SIthamar R. Adema Transport::Transport(const BPath& path) 11962cb58a8SIthamar R. Adema : BHandler(B_EMPTY_STRING), 120eb5a25caSIthamar R. Adema fPath(path), 12162cb58a8SIthamar R. Adema fImageID(-1), 12262cb58a8SIthamar R. Adema fFeatures(0) 12362cb58a8SIthamar R. Adema { 12462cb58a8SIthamar R. Adema // Load transport addon 12562cb58a8SIthamar R. Adema image_id id = ::load_add_on(path.Path()); 12662cb58a8SIthamar R. Adema if (id < B_OK) 12762cb58a8SIthamar R. Adema return; 12862cb58a8SIthamar R. Adema 12962cb58a8SIthamar R. Adema // Find transport_features symbol, to determine if we need to keep 13062cb58a8SIthamar R. Adema // this transport loaded 131*1797be0dSStefano Ceccherini int* transportFeaturesPointer; 13262cb58a8SIthamar R. Adema if (get_image_symbol(id, B_TRANSPORT_FEATURES_SYMBOL, 133*1797be0dSStefano Ceccherini B_SYMBOL_TYPE_DATA, (void**)&transportFeaturesPointer) != B_OK) { 13462cb58a8SIthamar R. Adema unload_add_on(id); 13562cb58a8SIthamar R. Adema } else { 136*1797be0dSStefano Ceccherini fFeatures = *transportFeaturesPointer; 13762cb58a8SIthamar R. Adema 138*1797be0dSStefano Ceccherini if (fFeatures & B_TRANSPORT_IS_HOTPLUG) { 139eb5a25caSIthamar R. Adema // We are hotpluggable; so keep us loaded! 14062cb58a8SIthamar R. Adema fImageID = id; 141*1797be0dSStefano Ceccherini } else { 142*1797be0dSStefano Ceccherini // No extended Transport support; so no need to keep loaded 14362cb58a8SIthamar R. Adema ::unload_add_on(id); 14462cb58a8SIthamar R. Adema } 145*1797be0dSStefano Ceccherini } 14662cb58a8SIthamar R. Adema 14762cb58a8SIthamar R. Adema sTransports.AddItem(this); 14862cb58a8SIthamar R. Adema } 14962cb58a8SIthamar R. Adema 1509abbe87fSMichael Pfeiffer 15162cb58a8SIthamar R. Adema Transport::~Transport() 15262cb58a8SIthamar R. Adema { 15362cb58a8SIthamar R. Adema sTransports.RemoveItem(this); 15462cb58a8SIthamar R. Adema } 15562cb58a8SIthamar R. Adema 1569abbe87fSMichael Pfeiffer 1579abbe87fSMichael Pfeiffer status_t 1589abbe87fSMichael Pfeiffer Transport::ListAvailablePorts(BMessage* msg) 159eb5a25caSIthamar R. Adema { 160eb5a25caSIthamar R. Adema status_t (*list_ports)(BMessage*); 161eb5a25caSIthamar R. Adema image_id id = fImageID; 162eb5a25caSIthamar R. Adema status_t rc = B_OK; 163eb5a25caSIthamar R. Adema 164eb5a25caSIthamar R. Adema // Load image if not loaded yet 165eb5a25caSIthamar R. Adema if (id == -1 && (id = load_add_on(fPath.Path())) < 0) 166eb5a25caSIthamar R. Adema return id; 167eb5a25caSIthamar R. Adema 168eb5a25caSIthamar R. Adema // Get pointer to addon function 169eb5a25caSIthamar R. Adema if ((rc = get_image_symbol(id, B_TRANSPORT_LIST_PORTS_SYMBOL, 170eb5a25caSIthamar R. Adema B_SYMBOL_TYPE_TEXT, (void**)&list_ports)) != B_OK) 171eb5a25caSIthamar R. Adema goto done; 172eb5a25caSIthamar R. Adema 173eb5a25caSIthamar R. Adema // run addon... 174eb5a25caSIthamar R. Adema rc = (*list_ports)(msg); 175eb5a25caSIthamar R. Adema 176eb5a25caSIthamar R. Adema done: 177eb5a25caSIthamar R. Adema // clean up if needed 178eb5a25caSIthamar R. Adema if (fImageID != id) 179eb5a25caSIthamar R. Adema unload_add_on(id); 180eb5a25caSIthamar R. Adema 181eb5a25caSIthamar R. Adema return rc; 182eb5a25caSIthamar R. Adema } 183eb5a25caSIthamar R. Adema 1849abbe87fSMichael Pfeiffer 185eb5a25caSIthamar R. Adema // --------------------------------------------------------------- 18662cb58a8SIthamar R. Adema // MessageReceived 18762cb58a8SIthamar R. Adema // 18862cb58a8SIthamar R. Adema // Handle scripting messages. 18962cb58a8SIthamar R. Adema // 19062cb58a8SIthamar R. Adema // Parameters: 19162cb58a8SIthamar R. Adema // msg - message. 19262cb58a8SIthamar R. Adema // --------------------------------------------------------------- 1939abbe87fSMichael Pfeiffer void 1949abbe87fSMichael Pfeiffer Transport::MessageReceived(BMessage* msg) 19562cb58a8SIthamar R. Adema { 19662cb58a8SIthamar R. Adema switch(msg->what) { 19762cb58a8SIthamar R. Adema case B_GET_PROPERTY: 19862cb58a8SIthamar R. Adema case B_SET_PROPERTY: 19962cb58a8SIthamar R. Adema case B_CREATE_PROPERTY: 20062cb58a8SIthamar R. Adema case B_DELETE_PROPERTY: 20162cb58a8SIthamar R. Adema case B_COUNT_PROPERTIES: 20262cb58a8SIthamar R. Adema case B_EXECUTE_PROPERTY: 20362cb58a8SIthamar R. Adema HandleScriptingCommand(msg); 20462cb58a8SIthamar R. Adema break; 20562cb58a8SIthamar R. Adema 20662cb58a8SIthamar R. Adema default: 20762cb58a8SIthamar R. Adema Inherited::MessageReceived(msg); 20862cb58a8SIthamar R. Adema } 20962cb58a8SIthamar R. Adema } 210