* Fixed the most annoying style violations of the files I had to look at - there
are still plenty of them left, though. Hey Jonas, we do have a coding style guideline! * Removed an extra copy of the message passed in to the settings constructor. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@18571 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -1,140 +1,120 @@
|
|||||||
// license: public domain
|
/*
|
||||||
// authors: [email protected]
|
* Copyright 2003-2006, Haiku, Inc. All Rights Reserved.
|
||||||
|
* Distributed under the terms of the MIT License.
|
||||||
|
*
|
||||||
|
* Authors:
|
||||||
|
* Jonas Sundström, [email protected]
|
||||||
|
*/
|
||||||
|
|
||||||
//
|
|
||||||
// TODO: proper locking <<---------
|
// TODO: proper locking <<---------
|
||||||
//
|
|
||||||
|
#include "ZipOMaticMisc.h"
|
||||||
|
#include "ZipOMaticSettings.h"
|
||||||
|
|
||||||
#include <Debug.h>
|
#include <Debug.h>
|
||||||
|
|
||||||
#include <VolumeRoster.h>
|
#include <VolumeRoster.h>
|
||||||
#include <FindDirectory.h>
|
#include <FindDirectory.h>
|
||||||
#include <Directory.h>
|
#include <Directory.h>
|
||||||
#include <Path.h>
|
#include <Path.h>
|
||||||
#include <File.h>
|
#include <File.h>
|
||||||
|
|
||||||
#include "ZipOMaticMisc.h"
|
|
||||||
#include "ZipOMaticSettings.h"
|
|
||||||
|
|
||||||
ZippoSettings::ZippoSettings()
|
ZippoSettings::ZippoSettings()
|
||||||
: BMessage (),
|
:
|
||||||
m_volume (),
|
fBaseDir(B_USER_SETTINGS_DIRECTORY)
|
||||||
m_base_dir (B_USER_SETTINGS_DIRECTORY),
|
|
||||||
m_relative_path (),
|
|
||||||
m_settings_filename ()
|
|
||||||
{
|
{
|
||||||
PRINT(("ZippoSettings()\n"));
|
PRINT(("ZippoSettings()\n"));
|
||||||
}
|
}
|
||||||
|
|
||||||
ZippoSettings::ZippoSettings(BMessage a_message)
|
|
||||||
: BMessage (a_message),
|
ZippoSettings::ZippoSettings(BMessage& message)
|
||||||
m_volume (),
|
: BMessage(message),
|
||||||
m_base_dir (B_USER_SETTINGS_DIRECTORY),
|
fBaseDir(B_USER_SETTINGS_DIRECTORY)
|
||||||
m_relative_path (),
|
|
||||||
m_settings_filename ()
|
|
||||||
{
|
{
|
||||||
PRINT(("ZippoSettings(a_message)\n"));
|
PRINT(("ZippoSettings(a_message)\n"));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
ZippoSettings::~ZippoSettings()
|
ZippoSettings::~ZippoSettings()
|
||||||
{
|
{
|
||||||
m_volume.Unset();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
ZippoSettings::SetTo (const char * a_settings_filename,
|
ZippoSettings::SetTo(const char* filename, BVolume* volume,
|
||||||
BVolume * a_volume,
|
directory_which baseDir, const char* relativePath)
|
||||||
directory_which a_base_dir,
|
|
||||||
const char * a_relative_path)
|
|
||||||
{
|
{
|
||||||
status_t status = B_OK;
|
status_t status = B_OK;
|
||||||
|
|
||||||
// copy to members
|
// copy to members
|
||||||
m_base_dir = a_base_dir;
|
fBaseDir = baseDir;
|
||||||
m_relative_path = a_relative_path;
|
fRelativePath = relativePath;
|
||||||
m_settings_filename = a_settings_filename;
|
fFilename = filename;
|
||||||
|
|
||||||
// sanity check
|
// sanity check
|
||||||
if (a_volume == NULL)
|
if (volume == NULL) {
|
||||||
{
|
BVolumeRoster volumeRoster;
|
||||||
BVolumeRoster volume_roster;
|
volumeRoster.GetBootVolume(&fVolume);
|
||||||
volume_roster.GetBootVolume(& m_volume);
|
} else
|
||||||
}
|
fVolume = *volume;
|
||||||
else
|
|
||||||
m_volume = *(a_volume);
|
status = fVolume.InitCheck();
|
||||||
|
|
||||||
status = m_volume.InitCheck();
|
|
||||||
if (status != B_OK)
|
if (status != B_OK)
|
||||||
return status;
|
return status;
|
||||||
|
|
||||||
// InitCheck
|
|
||||||
return InitCheck();
|
return InitCheck();
|
||||||
}
|
}
|
||||||
|
|
||||||
status_t
|
|
||||||
ZippoSettings::InitCheck (void)
|
|
||||||
{
|
|
||||||
BFile settings_file;
|
|
||||||
|
|
||||||
return GetSettingsFile (& settings_file, B_READ_ONLY | B_CREATE_FILE);
|
|
||||||
}
|
|
||||||
|
|
||||||
status_t
|
|
||||||
ZippoSettings::GetSettingsFile (BFile * a_settings_file, uint32 a_openmode)
|
|
||||||
{
|
|
||||||
status_t status = B_OK;
|
|
||||||
BPath settings_path;
|
|
||||||
|
|
||||||
status = find_and_create_directory(m_base_dir, & m_volume, m_relative_path.String(), & settings_path);
|
|
||||||
if (status != B_OK)
|
|
||||||
return status;
|
|
||||||
|
|
||||||
status = settings_path.Append (m_settings_filename.String());
|
|
||||||
if (status != B_OK)
|
|
||||||
return status;
|
|
||||||
|
|
||||||
status = a_settings_file->SetTo (settings_path.Path(), a_openmode);
|
|
||||||
if (status != B_OK)
|
|
||||||
return status;
|
|
||||||
|
|
||||||
return B_OK;
|
|
||||||
}
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
ZippoSettings::ReadSettings (void)
|
ZippoSettings::InitCheck()
|
||||||
|
{
|
||||||
|
BFile file;
|
||||||
|
return _GetSettingsFile(&file, B_READ_ONLY | B_CREATE_FILE);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
ZippoSettings::ReadSettings()
|
||||||
{
|
{
|
||||||
PRINT(("ZippoSettings::ReadSettings()\n"));
|
PRINT(("ZippoSettings::ReadSettings()\n"));
|
||||||
|
|
||||||
status_t status = B_OK;
|
BFile file;
|
||||||
BFile settings_file;
|
status_t status = _GetSettingsFile(&file, B_READ_ONLY);
|
||||||
|
|
||||||
status = GetSettingsFile (& settings_file, B_READ_ONLY);
|
|
||||||
if (status != B_OK)
|
|
||||||
return status;
|
|
||||||
|
|
||||||
status = Unflatten(& settings_file);
|
|
||||||
if (status != B_OK)
|
if (status != B_OK)
|
||||||
return status;
|
return status;
|
||||||
|
|
||||||
return B_OK;
|
return Unflatten(&file);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
ZippoSettings::WriteSettings (void)
|
ZippoSettings::WriteSettings()
|
||||||
{
|
{
|
||||||
PRINT(("ZippoSettings::WriteSettings()\n"));
|
PRINT(("ZippoSettings::WriteSettings()\n"));
|
||||||
|
|
||||||
status_t status = B_OK;
|
BFile file;
|
||||||
BFile settings_file;
|
status_t status = _GetSettingsFile(&file, B_WRITE_ONLY | B_ERASE_FILE);
|
||||||
|
|
||||||
status = GetSettingsFile (& settings_file, B_WRITE_ONLY | B_ERASE_FILE);
|
|
||||||
if (status != B_OK)
|
|
||||||
return status;
|
|
||||||
|
|
||||||
status = Flatten(& settings_file);
|
|
||||||
if (status != B_OK)
|
if (status != B_OK)
|
||||||
return status;
|
return status;
|
||||||
|
|
||||||
return B_OK;
|
return Flatten(&file);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
status_t
|
||||||
|
ZippoSettings::_GetSettingsFile(BFile* file, uint32 openMode)
|
||||||
|
{
|
||||||
|
BPath path;
|
||||||
|
status_t status = find_and_create_directory(fBaseDir, &fVolume,
|
||||||
|
fRelativePath.String(), &path);
|
||||||
|
if (status != B_OK)
|
||||||
|
return status;
|
||||||
|
|
||||||
|
status = path.Append(fFilename.String());
|
||||||
|
if (status != B_OK)
|
||||||
|
return status;
|
||||||
|
|
||||||
|
return file->SetTo(path.Path(), openMode);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,36 +1,42 @@
|
|||||||
#ifndef __ZIPPO_SETTINGS_H__
|
/*
|
||||||
#define __ZIPPO_SETTINGS_H__
|
* Copyright 2003-2006, Haiku, Inc. All Rights Reserved.
|
||||||
|
* Distributed under the terms of the MIT License.
|
||||||
|
*
|
||||||
|
* Authors:
|
||||||
|
* Jonas Sundström, [email protected]
|
||||||
|
*/
|
||||||
|
#ifndef ZIPOMATIC_SETTINGS_H
|
||||||
|
#define ZIPOMATIC_SETTINGS_H
|
||||||
|
|
||||||
|
|
||||||
|
#include <FindDirectory.h>
|
||||||
#include <Message.h>
|
#include <Message.h>
|
||||||
#include <Volume.h>
|
|
||||||
#include <String.h>
|
#include <String.h>
|
||||||
|
#include <Volume.h>
|
||||||
|
|
||||||
class ZippoSettings : public BMessage
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
ZippoSettings ();
|
|
||||||
ZippoSettings (BMessage a_message);
|
|
||||||
~ZippoSettings ();
|
|
||||||
|
|
||||||
status_t SetTo (const char * a_settings_filename,
|
|
||||||
BVolume * a_volume = NULL,
|
|
||||||
directory_which a_base_dir = B_USER_SETTINGS_DIRECTORY,
|
|
||||||
const char * a_relative_path = NULL);
|
|
||||||
|
|
||||||
status_t InitCheck (void);
|
class ZippoSettings : public BMessage {
|
||||||
|
public:
|
||||||
status_t ReadSettings ();
|
ZippoSettings();
|
||||||
status_t WriteSettings ();
|
ZippoSettings(BMessage& message);
|
||||||
|
~ZippoSettings();
|
||||||
private:
|
|
||||||
|
|
||||||
status_t GetSettingsFile (BFile * a_settings_file, uint32 a_openmode);
|
status_t SetTo(const char* filename, BVolume* volume = NULL,
|
||||||
|
directory_which baseDir = B_USER_SETTINGS_DIRECTORY,
|
||||||
|
const char* relativePath = NULL);
|
||||||
|
|
||||||
BVolume m_volume;
|
status_t InitCheck();
|
||||||
directory_which m_base_dir;
|
|
||||||
BString m_relative_path;
|
|
||||||
BString m_settings_filename;
|
|
||||||
|
|
||||||
|
status_t ReadSettings();
|
||||||
|
status_t WriteSettings();
|
||||||
|
|
||||||
|
private:
|
||||||
|
status_t _GetSettingsFile(BFile* file, uint32 openMode);
|
||||||
|
|
||||||
|
BVolume fVolume;
|
||||||
|
directory_which fBaseDir;
|
||||||
|
BString fRelativePath;
|
||||||
|
BString fFilename;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // __ZIPPO_SETTINGS_H__
|
#endif // ZIPOMATIC_SETTINGS_H
|
||||||
|
|||||||
@@ -1,162 +1,153 @@
|
|||||||
// license: public domain
|
/*
|
||||||
// authors: [email protected]
|
* Copyright 2003-2006, Haiku, Inc. All Rights Reserved.
|
||||||
//
|
* Distributed under the terms of the MIT License.
|
||||||
// exception: ZipperThread::PipeCommand()
|
*
|
||||||
// written by Peter Folk, published in the BeDevTalk mailinglist FAQ
|
* Authors:
|
||||||
// License unknown, most likely public domain
|
* Jonas Sundström, [email protected]
|
||||||
|
*/
|
||||||
|
|
||||||
#include <Debug.h>
|
|
||||||
|
|
||||||
#include <Path.h>
|
|
||||||
|
|
||||||
#include "ZipOMaticZipper.h"
|
#include "ZipOMaticZipper.h"
|
||||||
#include "ZipOMaticWindow.h"
|
#include "ZipOMaticWindow.h"
|
||||||
#include "ZipOMaticMisc.h"
|
#include "ZipOMaticMisc.h"
|
||||||
|
|
||||||
|
#include <Debug.h>
|
||||||
|
#include <FindDirectory.h>
|
||||||
|
#include <Message.h>
|
||||||
|
#include <Path.h>
|
||||||
|
#include <Volume.h>
|
||||||
|
|
||||||
|
#include <String.h>
|
||||||
|
#include <Window.h>
|
||||||
|
#include <OS.h>
|
||||||
|
|
||||||
#include <signal.h>
|
#include <signal.h>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#include <errno.h>
|
#include <errno.h>
|
||||||
|
|
||||||
const char * ZipperThreadName = "ZipperThread";
|
|
||||||
|
const char* kZipperThreadName = "ZipperThread";
|
||||||
|
|
||||||
|
|
||||||
ZipperThread::ZipperThread (BMessage * a_refs_message, BWindow * a_window)
|
ZipperThread::ZipperThread (BMessage* refsMessage, BWindow* window)
|
||||||
: GenericThread(ZipperThreadName, B_NORMAL_PRIORITY, a_refs_message),
|
: GenericThread(kZipperThreadName, B_NORMAL_PRIORITY, refsMessage),
|
||||||
m_window (a_window),
|
fWindowMessenger(window),
|
||||||
m_window_messenger (new BMessenger(NULL, a_window)),
|
m_zip_process_thread_id(-1),
|
||||||
m_zip_process_thread_id (-1),
|
m_std_in(-1),
|
||||||
m_std_in (-1),
|
m_std_out(-1),
|
||||||
m_std_out (-1),
|
m_std_err(-1),
|
||||||
m_std_err (-1),
|
fOutputFile(NULL)
|
||||||
m_zip_output (NULL),
|
|
||||||
m_zip_output_string (),
|
|
||||||
m_zip_output_buffer (new char [4096])
|
|
||||||
{
|
{
|
||||||
PRINT(("ZipperThread()\n"));
|
PRINT(("ZipperThread()\n"));
|
||||||
|
|
||||||
m_thread_data_store = new BMessage (* a_refs_message); // leak?
|
m_thread_data_store = new BMessage(*refsMessage);
|
||||||
// prevents bug with B_SIMPLE_DATA
|
// leak?
|
||||||
// (drag&drop messages)
|
// prevents bug with B_SIMPLE_DATA
|
||||||
|
// (drag&drop messages)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
ZipperThread::~ZipperThread()
|
ZipperThread::~ZipperThread()
|
||||||
{
|
{
|
||||||
delete m_window_messenger;
|
|
||||||
delete [] m_zip_output_buffer;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
ZipperThread::ThreadStartup (void)
|
ZipperThread::ThreadStartup()
|
||||||
{
|
{
|
||||||
PRINT(("ZipperThread::ThreadStartup()\n"));
|
PRINT(("ZipperThread::ThreadStartup()\n"));
|
||||||
|
|
||||||
// init
|
// init
|
||||||
status_t status = B_OK;
|
status_t status = B_OK;
|
||||||
entry_ref ref;
|
entry_ref ref;
|
||||||
entry_ref last_ref;
|
entry_ref last_ref;
|
||||||
bool same_folder = true;
|
bool same_folder = true;
|
||||||
|
|
||||||
|
BString zip_archive_filename = "Archive.zip";
|
||||||
|
|
||||||
BString zip_archive_filename = "Archive.zip";
|
|
||||||
|
|
||||||
// do all refs have the same parent dir?
|
// do all refs have the same parent dir?
|
||||||
type_code ref_type = B_REF_TYPE;
|
type_code ref_type = B_REF_TYPE;
|
||||||
int32 ref_count = 0;
|
int32 ref_count = 0;
|
||||||
|
|
||||||
status = m_thread_data_store->GetInfo("refs", & ref_type, & ref_count);
|
status = m_thread_data_store->GetInfo("refs", &ref_type, &ref_count);
|
||||||
if (status != B_OK)
|
if (status != B_OK)
|
||||||
return status;
|
return status;
|
||||||
|
|
||||||
for (int index = 0; index < ref_count ; index++)
|
for (int index = 0; index < ref_count ; index++) {
|
||||||
{
|
|
||||||
m_thread_data_store->FindRef("refs", index, & ref);
|
m_thread_data_store->FindRef("refs", index, & ref);
|
||||||
|
|
||||||
if (index > 0)
|
if (index > 0) {
|
||||||
{
|
BEntry entry(&ref);
|
||||||
BEntry entry (& ref);
|
if (entry.IsSymLink()) {
|
||||||
if (entry.IsSymLink())
|
|
||||||
{
|
|
||||||
entry.SetTo(& ref, true);
|
entry.SetTo(& ref, true);
|
||||||
entry_ref target;
|
entry_ref target;
|
||||||
entry.GetRef(& target);
|
entry.GetRef(& target);
|
||||||
if (last_ref.directory != target.directory)
|
if (last_ref.directory != target.directory) {
|
||||||
{
|
same_folder = false;
|
||||||
same_folder = false;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
} else if (last_ref.directory != ref.directory) {
|
||||||
else
|
same_folder = false;
|
||||||
if (last_ref.directory != ref.directory)
|
|
||||||
{
|
|
||||||
same_folder = false;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
last_ref = ref;
|
last_ref = ref;
|
||||||
}
|
}
|
||||||
|
|
||||||
// change active dir
|
// change active dir
|
||||||
if (same_folder)
|
if (same_folder) {
|
||||||
{
|
BEntry entry(&last_ref);
|
||||||
BEntry entry (& last_ref);
|
|
||||||
BPath path;
|
BPath path;
|
||||||
entry.GetParent(& entry);
|
entry.GetParent(&entry);
|
||||||
entry.GetPath(& path);
|
entry.GetPath(&path);
|
||||||
chdir(path.Path());
|
chdir(path.Path());
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
BPath path;
|
BPath path;
|
||||||
if (find_directory(B_DESKTOP_DIRECTORY, & path) == B_OK)
|
if (find_directory(B_DESKTOP_DIRECTORY, &path) == B_OK)
|
||||||
chdir (path.Path());
|
chdir(path.Path());
|
||||||
}
|
}
|
||||||
|
|
||||||
// archive filename
|
// archive filename
|
||||||
if (ref_count == 1)
|
if (ref_count == 1) {
|
||||||
{
|
zip_archive_filename = last_ref.name;
|
||||||
zip_archive_filename = last_ref.name;
|
zip_archive_filename += ".zip";
|
||||||
zip_archive_filename += ".zip";
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int32 argc = ref_count + 3;
|
|
||||||
const char ** argv = new const char * [argc + 1];
|
|
||||||
|
|
||||||
argv[0] = strdup("/bin/zip");
|
|
||||||
argv[1] = strdup("-ry");
|
|
||||||
argv[2] = strdup(zip_archive_filename.String());
|
|
||||||
|
|
||||||
|
|
||||||
// files to zip
|
|
||||||
for (int ref_index = 0; ref_index < ref_count ; ref_index++)
|
|
||||||
{
|
|
||||||
m_thread_data_store->FindRef("refs", ref_index, & ref);
|
|
||||||
|
|
||||||
if (same_folder)
|
|
||||||
{
|
|
||||||
argv[3 + ref_index] = strdup(ref.name); // just the file name
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
BPath path (& ref);
|
|
||||||
BString file = path.Path();
|
|
||||||
argv[3 + ref_index] = strdup(path.Path()); // full path
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
argv[argc] = NULL;
|
|
||||||
|
|
||||||
m_zip_process_thread_id = PipeCommand (argc, argv, m_std_in, m_std_out, m_std_err);
|
int32 argc = ref_count + 3;
|
||||||
|
const char** argv = new const char* [argc + 1];
|
||||||
|
|
||||||
|
argv[0] = strdup("/bin/zip");
|
||||||
|
argv[1] = strdup("-ry");
|
||||||
|
argv[2] = strdup(zip_archive_filename.String());
|
||||||
|
|
||||||
|
// files to zip
|
||||||
|
for (int ref_index = 0; ref_index < ref_count ; ref_index++) {
|
||||||
|
m_thread_data_store->FindRef("refs", ref_index, &ref);
|
||||||
|
|
||||||
|
if (same_folder) {
|
||||||
|
argv[3 + ref_index] = strdup(ref.name); // just the file name
|
||||||
|
} else {
|
||||||
|
BPath path(&ref);
|
||||||
|
BString file = path.Path();
|
||||||
|
argv[3 + ref_index] = strdup(path.Path()); // full path
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
argv[argc] = NULL;
|
||||||
|
|
||||||
|
m_zip_process_thread_id = PipeCommand(argc, argv, m_std_in, m_std_out, m_std_err);
|
||||||
|
|
||||||
delete [] argv;
|
delete [] argv;
|
||||||
|
|
||||||
if (m_zip_process_thread_id < 0)
|
if (m_zip_process_thread_id < 0)
|
||||||
return (m_zip_process_thread_id);
|
return m_zip_process_thread_id;
|
||||||
|
|
||||||
resume_thread (m_zip_process_thread_id);
|
resume_thread(m_zip_process_thread_id);
|
||||||
|
|
||||||
m_zip_output = fdopen (m_std_out, "r");
|
fOutputFile = fdopen(m_std_out, "r");
|
||||||
|
|
||||||
zip_archive_filename.Prepend("Creating archive: ");
|
zip_archive_filename.Prepend("Creating archive: ");
|
||||||
|
|
||||||
SendMessageToWindow ('strt', "archive_filename", zip_archive_filename.String());
|
SendMessageToWindow ('strt', "archive_filename", zip_archive_filename.String());
|
||||||
SendMessageToWindow ('outp', "zip_output", "Preparing to archive");
|
SendMessageToWindow ('outp', "zip_output", "Preparing to archive");
|
||||||
|
|
||||||
@@ -165,48 +156,40 @@ ZipperThread::ThreadStartup (void)
|
|||||||
return B_OK;
|
return B_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
ZipperThread::ExecuteUnit (void)
|
ZipperThread::ExecuteUnit()
|
||||||
{
|
{
|
||||||
//PRINT(("ZipperThread::ExecuteUnit()\n"));
|
//PRINT(("ZipperThread::ExecuteUnit()\n"));
|
||||||
|
|
||||||
// read output from /bin/zip
|
// read output from /bin/zip
|
||||||
// send it to window
|
// send it to window
|
||||||
|
char buffer[4096];
|
||||||
char * output_string;
|
|
||||||
output_string = fgets(m_zip_output_buffer , 4096-1, m_zip_output);
|
|
||||||
|
|
||||||
if (output_string == NULL)
|
char* output = fgets(buffer, sizeof(buffer) - 1, fOutputFile);
|
||||||
{
|
if (output == NULL)
|
||||||
return EOF;
|
return EOF;
|
||||||
}
|
|
||||||
else
|
char* newLine = strrchr(output, '\n');
|
||||||
{
|
if (newLine != NULL)
|
||||||
char * new_line_ptr = strrchr(output_string, '\n');
|
*newLine = '\0';
|
||||||
if (new_line_ptr != NULL)
|
|
||||||
*new_line_ptr = '\0';
|
if (!strncmp(" a", output, 3)) {
|
||||||
|
output[2] = 'A';
|
||||||
if (! strncmp(" a", m_zip_output_buffer, 3))
|
SendMessageToWindow('outp', "zip_output", output + 2);
|
||||||
{
|
} else if (!strncmp("up", output, 2)) {
|
||||||
m_zip_output_buffer[2] = 'A';
|
output[0] = 'U';
|
||||||
SendMessageToWindow ('outp', "zip_output", output_string + 2);
|
SendMessageToWindow('outp', "zip_output", output);
|
||||||
}
|
} else {
|
||||||
else if (! strncmp("up", m_zip_output_buffer, 2))
|
SendMessageToWindow('outp', "zip_output", output);
|
||||||
{
|
|
||||||
m_zip_output_buffer[0] = 'U';
|
|
||||||
SendMessageToWindow ('outp', "zip_output", output_string);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
SendMessageToWindow ('outp', "zip_output", output_string);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return B_OK;
|
return B_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
ZipperThread::ThreadShutdown (void)
|
ZipperThread::ThreadShutdown()
|
||||||
{
|
{
|
||||||
PRINT(("ZipperThread::ThreadShutdown()\n"));
|
PRINT(("ZipperThread::ThreadShutdown()\n"));
|
||||||
|
|
||||||
@@ -217,172 +200,184 @@ ZipperThread::ThreadShutdown (void)
|
|||||||
return B_OK;
|
return B_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
|
||||||
ZipperThread::ThreadStartupFailed (status_t a_status)
|
|
||||||
{
|
|
||||||
error_message("ZipperThread::ThreadStartupFailed() \n", a_status);
|
|
||||||
|
|
||||||
|
void
|
||||||
|
ZipperThread::ThreadStartupFailed(status_t status)
|
||||||
|
{
|
||||||
|
error_message("ZipperThread::ThreadStartupFailed() \n", status);
|
||||||
Quit();
|
Quit();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
ZipperThread::ExecuteUnitFailed (status_t a_status)
|
ZipperThread::ExecuteUnitFailed(status_t status)
|
||||||
{
|
{
|
||||||
error_message("ZipperThread::ExecuteUnitFailed() \n", a_status);
|
error_message("ZipperThread::ExecuteUnitFailed() \n", status);
|
||||||
|
|
||||||
|
if (status == EOF) {
|
||||||
if (a_status == EOF)
|
|
||||||
{
|
|
||||||
// thread has finished, been quit or killed, we don't know
|
// thread has finished, been quit or killed, we don't know
|
||||||
SendMessageToWindow ('exit');
|
SendMessageToWindow('exit');
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
// explicit error - communicate error to Window
|
// explicit error - communicate error to Window
|
||||||
SendMessageToWindow ('exrr');
|
SendMessageToWindow('exrr');
|
||||||
}
|
}
|
||||||
|
|
||||||
Quit();
|
Quit();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
ZipperThread::ThreadShutdownFailed (status_t a_status)
|
ZipperThread::ThreadShutdownFailed(status_t status)
|
||||||
{
|
{
|
||||||
error_message("ZipperThread::ThreadShutdownFailed() \n", a_status);
|
error_message("ZipperThread::ThreadShutdownFailed() \n", status);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void
|
void
|
||||||
ZipperThread::MakeShellSafe (BString * a_string)
|
ZipperThread::MakeShellSafe(BString* string)
|
||||||
{
|
{
|
||||||
a_string->CharacterEscape("\"$`", '\\');
|
string->CharacterEscape("\"$`", '\\');
|
||||||
a_string->Prepend("\"");
|
string->Prepend("\"");
|
||||||
a_string->Append("\"");
|
string->Append("\"");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
ZipperThread::ProcessRefs (BMessage * msg)
|
ZipperThread::ProcessRefs(BMessage* msg)
|
||||||
{
|
{
|
||||||
|
|
||||||
return B_OK;
|
return B_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
thread_id
|
thread_id
|
||||||
ZipperThread::PipeCommand (int argc, const char **argv, int & in, int & out, int & err, const char **envp)
|
ZipperThread::PipeCommand(int argc, const char** argv, int& in, int& out,
|
||||||
{
|
int& err, const char** envp)
|
||||||
|
{
|
||||||
// This function written by Peter Folk <[email protected]>
|
// This function written by Peter Folk <[email protected]>
|
||||||
// and published in the BeDevTalk FAQ
|
// and published in the BeDevTalk FAQ
|
||||||
// http://www.abisoft.com/faq/BeDevTalk_FAQ.html#FAQ-209
|
// http://www.abisoft.com/faq/BeDevTalk_FAQ.html#FAQ-209
|
||||||
|
|
||||||
// Save current FDs
|
// Save current FDs
|
||||||
int old_in = dup(0);
|
int old_in = dup(0);
|
||||||
int old_out = dup(1);
|
int old_out = dup(1);
|
||||||
int old_err = dup(2);
|
int old_err = dup(2);
|
||||||
|
|
||||||
int filedes[2];
|
int filedes[2];
|
||||||
|
|
||||||
/* Create new pipe FDs as stdin, stdout, stderr */
|
/* Create new pipe FDs as stdin, stdout, stderr */
|
||||||
pipe(filedes); dup2(filedes[0],0); close(filedes[0]);
|
pipe(filedes);
|
||||||
in=filedes[1]; // Write to in, appears on cmd's stdin
|
dup2(filedes[0], 0);
|
||||||
pipe(filedes); dup2(filedes[1],1); close(filedes[1]);
|
close(filedes[0]);
|
||||||
out=filedes[0]; // Read from out, taken from cmd's stdout
|
in = filedes[1]; // Write to in, appears on cmd's stdin
|
||||||
pipe(filedes); dup2(filedes[1],2); close(filedes[1]);
|
pipe(filedes);
|
||||||
err=filedes[0]; // Read from err, taken from cmd's stderr
|
dup2(filedes[1], 1);
|
||||||
|
close(filedes[1]);
|
||||||
// "load" command.
|
out = filedes[0]; // Read from out, taken from cmd's stdout
|
||||||
thread_id ret = load_image(argc, argv, envp);
|
pipe(filedes);
|
||||||
// thread ret is now suspended.
|
dup2(filedes[1], 2);
|
||||||
|
close(filedes[1]);
|
||||||
|
err = filedes[0]; // Read from err, taken from cmd's stderr
|
||||||
|
|
||||||
|
// "load" command.
|
||||||
|
thread_id ret = load_image(argc, argv, envp);
|
||||||
|
// thread ret is now suspended.
|
||||||
|
|
||||||
PRINT(("load_image() thread_id: %ld\n", ret));
|
PRINT(("load_image() thread_id: %ld\n", ret));
|
||||||
|
|
||||||
// Restore old FDs
|
// Restore old FDs
|
||||||
close(0); dup(old_in); close(old_in);
|
close(0); dup(old_in); close(old_in);
|
||||||
close(1); dup(old_out); close(old_out);
|
close(1); dup(old_out); close(old_out);
|
||||||
close(2); dup(old_err); close(old_err);
|
close(2); dup(old_err); close(old_err);
|
||||||
|
|
||||||
/* Theoretically I should do loads of error checking, but
|
// TODO:
|
||||||
the calls aren't very likely to fail, and that would
|
/*
|
||||||
muddy up the example quite a bit. YMMV. */
|
Theoretically I should do loads of error checking, but
|
||||||
|
the calls aren't very likely to fail, and that would
|
||||||
|
muddy up the example quite a bit. YMMV.
|
||||||
|
*/
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
void
|
||||||
ZipperThread::SendMessageToWindow (uint32 a_msg_what, const char * a_string_name, const char * a_string_value)
|
ZipperThread::SendMessageToWindow(uint32 what, const char* name, const char* value)
|
||||||
{
|
{
|
||||||
BMessage msg (a_msg_what);
|
BMessage msg(what);
|
||||||
|
if (name != NULL && value != NULL)
|
||||||
if (! (a_string_name == NULL || a_string_value == NULL))
|
msg.AddString(name, value);
|
||||||
msg.AddString(a_string_name, a_string_value);
|
|
||||||
|
fWindowMessenger.SendMessage(&msg);
|
||||||
m_window_messenger->SendMessage(& msg);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
ZipperThread::SuspendExternalZip (void)
|
ZipperThread::SuspendExternalZip()
|
||||||
{
|
{
|
||||||
PRINT(("ZipperThread::SuspendExternalZip()\n"));
|
PRINT(("ZipperThread::SuspendExternalZip()\n"));
|
||||||
|
|
||||||
status_t status = B_OK;
|
status_t status = B_OK;
|
||||||
thread_info zip_thread_info;
|
thread_info zip_thread_info;
|
||||||
status = get_thread_info (m_zip_process_thread_id, & zip_thread_info);
|
status = get_thread_info(m_zip_process_thread_id, &zip_thread_info);
|
||||||
BString thread_name = zip_thread_info.name;
|
BString thread_name = zip_thread_info.name;
|
||||||
|
|
||||||
if (status == B_OK && thread_name == "zip")
|
if (status == B_OK && thread_name == "zip")
|
||||||
return suspend_thread (m_zip_process_thread_id);
|
return suspend_thread (m_zip_process_thread_id);
|
||||||
else
|
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
ZipperThread::ResumeExternalZip (void)
|
ZipperThread::ResumeExternalZip()
|
||||||
{
|
{
|
||||||
PRINT(("ZipperThread::ResumeExternalZip()\n"));
|
PRINT(("ZipperThread::ResumeExternalZip()\n"));
|
||||||
|
|
||||||
status_t status = B_OK;
|
status_t status = B_OK;
|
||||||
thread_info zip_thread_info;
|
thread_info zip_thread_info;
|
||||||
status = get_thread_info (m_zip_process_thread_id, & zip_thread_info);
|
status = get_thread_info(m_zip_process_thread_id, &zip_thread_info);
|
||||||
BString thread_name = zip_thread_info.name;
|
BString thread_name = zip_thread_info.name;
|
||||||
|
|
||||||
if (status == B_OK && thread_name == "zip")
|
if (status == B_OK && thread_name == "zip")
|
||||||
return resume_thread (m_zip_process_thread_id);
|
return resume_thread(m_zip_process_thread_id);
|
||||||
else
|
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
ZipperThread::InterruptExternalZip (void)
|
ZipperThread::InterruptExternalZip()
|
||||||
{
|
{
|
||||||
PRINT(("ZipperThread::InterruptExternalZip()\n"));
|
PRINT(("ZipperThread::InterruptExternalZip()\n"));
|
||||||
|
|
||||||
status_t status = B_OK;
|
status_t status = B_OK;
|
||||||
thread_info zip_thread_info;
|
thread_info zip_thread_info;
|
||||||
status = get_thread_info (m_zip_process_thread_id, & zip_thread_info);
|
status = get_thread_info(m_zip_process_thread_id, &zip_thread_info);
|
||||||
BString thread_name = zip_thread_info.name;
|
BString thread_name = zip_thread_info.name;
|
||||||
|
|
||||||
if (status == B_OK && thread_name == "zip")
|
if (status == B_OK && thread_name == "zip") {
|
||||||
{
|
status = B_OK;
|
||||||
status = B_OK;
|
status = send_signal(m_zip_process_thread_id, SIGINT);
|
||||||
status = send_signal (m_zip_process_thread_id, SIGINT);
|
|
||||||
WaitOnExternalZip();
|
WaitOnExternalZip();
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
else
|
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
ZipperThread::WaitOnExternalZip (void)
|
ZipperThread::WaitOnExternalZip()
|
||||||
{
|
{
|
||||||
PRINT(("ZipperThread::WaitOnExternalZip()\n"));
|
PRINT(("ZipperThread::WaitOnExternalZip()\n"));
|
||||||
|
|
||||||
status_t status = B_OK;
|
status_t status = B_OK;
|
||||||
thread_info zip_thread_info;
|
thread_info zip_thread_info;
|
||||||
status = get_thread_info (m_zip_process_thread_id, & zip_thread_info);
|
status = get_thread_info(m_zip_process_thread_id, &zip_thread_info);
|
||||||
BString thread_name = zip_thread_info.name;
|
BString thread_name = zip_thread_info.name;
|
||||||
|
|
||||||
if (status == B_OK && thread_name == "zip")
|
if (status == B_OK && thread_name == "zip")
|
||||||
return wait_for_thread (m_zip_process_thread_id, & status);
|
return wait_for_thread(m_zip_process_thread_id, &status);
|
||||||
else
|
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,61 +1,60 @@
|
|||||||
#ifndef __ZIPOMATIC_ZIPPER_H__
|
/*
|
||||||
#define __ZIPOMATIC_ZIPPER_H__
|
* Copyright 2003-2006, Haiku, Inc. All Rights Reserved.
|
||||||
|
* Distributed under the terms of the MIT License.
|
||||||
|
*
|
||||||
|
* Authors:
|
||||||
|
* Jonas Sundström, [email protected]
|
||||||
|
*/
|
||||||
|
#ifndef ZIPPER_THREAD_H
|
||||||
|
#define ZIPPER_THREAD_H
|
||||||
|
|
||||||
#include <Message.h>
|
|
||||||
#include <Volume.h>
|
|
||||||
#include <String.h>
|
|
||||||
#include <Window.h>
|
|
||||||
#include <OS.h>
|
|
||||||
#include <FindDirectory.h>
|
|
||||||
|
|
||||||
#include "GenericThread.h"
|
#include "GenericThread.h"
|
||||||
#include <stdlib.h>
|
|
||||||
|
|
||||||
extern const char * ZipperThreadName;
|
#include <Messenger.h>
|
||||||
|
|
||||||
class ZipperThread : public GenericThread
|
#include <stdio.h>
|
||||||
{
|
|
||||||
public:
|
|
||||||
ZipperThread (BMessage * a_refs_message, BWindow * a_window);
|
|
||||||
~ZipperThread ();
|
|
||||||
|
|
||||||
status_t SuspendExternalZip (void);
|
class BMessage;
|
||||||
status_t ResumeExternalZip (void);
|
class BWindow;
|
||||||
status_t InterruptExternalZip (void);
|
|
||||||
status_t WaitOnExternalZip (void);
|
|
||||||
|
|
||||||
private:
|
|
||||||
|
|
||||||
virtual status_t ThreadStartup (void);
|
class ZipperThread : public GenericThread {
|
||||||
virtual status_t ExecuteUnit (void);
|
public:
|
||||||
virtual status_t ThreadShutdown (void);
|
ZipperThread(BMessage* refsMessage, BWindow* window);
|
||||||
|
~ZipperThread();
|
||||||
virtual void ThreadStartupFailed (status_t a_status);
|
|
||||||
virtual void ExecuteUnitFailed (status_t a_status);
|
|
||||||
virtual void ThreadShutdownFailed (status_t a_status);
|
|
||||||
|
|
||||||
status_t ProcessRefs (BMessage * msg);
|
status_t SuspendExternalZip();
|
||||||
void MakeShellSafe (BString * a_string);
|
status_t ResumeExternalZip();
|
||||||
|
status_t InterruptExternalZip();
|
||||||
thread_id PipeCommand (int argc, const char **argv,
|
status_t WaitOnExternalZip();
|
||||||
int & in, int & out, int & err,
|
|
||||||
const char **envp = (const char **) environ);
|
|
||||||
|
|
||||||
void SendMessageToWindow (uint32 a_msg_what,
|
|
||||||
const char * a_string_name = NULL,
|
|
||||||
const char * a_string_value = NULL);
|
|
||||||
|
|
||||||
BWindow * m_window;
|
|
||||||
BMessenger * m_window_messenger;
|
|
||||||
|
|
||||||
int32 m_zip_process_thread_id;
|
private:
|
||||||
int m_std_in;
|
virtual status_t ThreadStartup();
|
||||||
int m_std_out;
|
virtual status_t ExecuteUnit();
|
||||||
int m_std_err;
|
virtual status_t ThreadShutdown();
|
||||||
FILE * m_zip_output;
|
|
||||||
BString m_zip_output_string;
|
virtual void ThreadStartupFailed(status_t a_status);
|
||||||
char * m_zip_output_buffer;
|
virtual void ExecuteUnitFailed(status_t a_status);
|
||||||
|
virtual void ThreadShutdownFailed(status_t a_status);
|
||||||
|
|
||||||
|
status_t ProcessRefs(BMessage* msg);
|
||||||
|
void MakeShellSafe(BString* string);
|
||||||
|
|
||||||
|
thread_id PipeCommand(int argc, const char **argv,
|
||||||
|
int & in, int & out, int & err,
|
||||||
|
const char **envp = (const char **)environ);
|
||||||
|
|
||||||
|
void SendMessageToWindow(uint32 what,
|
||||||
|
const char* name = NULL, const char* value = NULL);
|
||||||
|
|
||||||
|
BMessenger fWindowMessenger;
|
||||||
|
int32 m_zip_process_thread_id;
|
||||||
|
int m_std_in;
|
||||||
|
int m_std_out;
|
||||||
|
int m_std_err;
|
||||||
|
FILE* fOutputFile;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // __ZIPOMATIC_ZIPPER_H__
|
#endif // ZIPPER_THREAD_H
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user