mirror of
https://github.com/juce-framework/JUCE.git
synced 2026-01-19 01:04:20 +00:00
This commit is contained in:
parent
88fa4e0e56
commit
ff3c2e9fce
9 changed files with 521 additions and 771 deletions
|
|
@ -57,48 +57,22 @@ BEGIN_JUCE_NAMESPACE
|
|||
#include "../../../src/juce_core/basics/juce_Time.h"
|
||||
#include "../../../src/juce_core/io/network/juce_URL.h"
|
||||
#include "../../../src/juce_core/io/files/juce_NamedPipe.h"
|
||||
#include "../../../src/juce_core/threads/juce_InterProcessLock.h"
|
||||
#include "../../../src/juce_core/threads/juce_Thread.h"
|
||||
|
||||
//==============================================================================
|
||||
/*
|
||||
Note that a lot of methods that you'd expect to find in this file actually
|
||||
live in juce_posix_SharedCode.cpp!
|
||||
*/
|
||||
#include "../../macosx/platform_specific_code/juce_posix_SharedCode.cpp"
|
||||
|
||||
|
||||
//==============================================================================
|
||||
static File executableFile;
|
||||
|
||||
|
||||
//==============================================================================
|
||||
bool juce_isDirectory (const String& fileName) throw()
|
||||
{
|
||||
if (fileName.isEmpty())
|
||||
return true;
|
||||
|
||||
struct stat info;
|
||||
const int res = stat (fileName.toUTF8(), &info);
|
||||
if (res == 0)
|
||||
return (info.st_mode & S_IFDIR) != 0;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool juce_fileExists (const String& fileName, const bool dontCountDirectories) throw()
|
||||
{
|
||||
if (fileName.isEmpty())
|
||||
return false;
|
||||
|
||||
bool exists = access (fileName.toUTF8(), F_OK) == 0;
|
||||
|
||||
if (exists && dontCountDirectories && juce_isDirectory (fileName))
|
||||
exists = false;
|
||||
|
||||
return exists;
|
||||
}
|
||||
|
||||
int64 juce_getFileSize (const String& fileName) throw()
|
||||
{
|
||||
struct stat info;
|
||||
const int res = stat (fileName.toUTF8(), &info);
|
||||
|
||||
if (res == 0)
|
||||
return info.st_size;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void juce_getFileTimes (const String& fileName,
|
||||
int64& modificationTime,
|
||||
int64& accessTime,
|
||||
|
|
@ -112,10 +86,6 @@ void juce_getFileTimes (const String& fileName,
|
|||
const int res = stat (fileName.toUTF8(), &info);
|
||||
if (res == 0)
|
||||
{
|
||||
/*
|
||||
* Note: On Linux the st_ctime field is defined as last change time
|
||||
* rather than creation.
|
||||
*/
|
||||
modificationTime = (int64) info.st_mtime * 1000;
|
||||
accessTime = (int64) info.st_atime * 1000;
|
||||
creationTime = (int64) info.st_ctime * 1000;
|
||||
|
|
@ -134,11 +104,6 @@ bool juce_setFileTimes (const String& fileName,
|
|||
return utime (fileName.toUTF8(), ×) == 0;
|
||||
}
|
||||
|
||||
bool juce_canWriteToFile (const String& fileName) throw()
|
||||
{
|
||||
return access (fileName.toUTF8(), W_OK) == 0;
|
||||
}
|
||||
|
||||
bool juce_setFileReadOnly (const String& fileName, bool isReadOnly) throw()
|
||||
{
|
||||
struct stat info;
|
||||
|
|
@ -157,14 +122,6 @@ bool juce_setFileReadOnly (const String& fileName, bool isReadOnly) throw()
|
|||
return chmod (fileName.toUTF8(), info.st_mode) == 0;
|
||||
}
|
||||
|
||||
bool juce_deleteFile (const String& fileName) throw()
|
||||
{
|
||||
if (juce_isDirectory (fileName))
|
||||
return rmdir (fileName.toUTF8()) == 0;
|
||||
else
|
||||
return remove (fileName.toUTF8()) == 0;
|
||||
}
|
||||
|
||||
bool juce_copyFile (const String& s, const String& d) throw()
|
||||
{
|
||||
const File source (s), dest (d);
|
||||
|
|
@ -196,97 +153,6 @@ bool juce_copyFile (const String& s, const String& d) throw()
|
|||
return ok;
|
||||
}
|
||||
|
||||
bool juce_moveFile (const String& source, const String& dest) throw()
|
||||
{
|
||||
if (rename (source.toUTF8(), dest.toUTF8()) == 0)
|
||||
return true;
|
||||
|
||||
if (! juce_canWriteToFile (source))
|
||||
return false;
|
||||
|
||||
if (juce_copyFile (source, dest))
|
||||
{
|
||||
if (juce_deleteFile (source))
|
||||
return true;
|
||||
|
||||
juce_deleteFile (dest);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
void juce_createDirectory (const String& fileName) throw()
|
||||
{
|
||||
mkdir (fileName.toUTF8(), 0777);
|
||||
}
|
||||
|
||||
void* juce_fileOpen (const String& fileName, bool forWriting) throw()
|
||||
{
|
||||
const char* mode = "rb";
|
||||
|
||||
if (forWriting)
|
||||
{
|
||||
if (juce_fileExists (fileName, false))
|
||||
{
|
||||
FILE* f = fopen (fileName.toUTF8(), "r+b");
|
||||
if (f != 0)
|
||||
fseek (f, 0, SEEK_END);
|
||||
|
||||
return (void*) f;
|
||||
}
|
||||
else
|
||||
{
|
||||
mode = "w+b";
|
||||
}
|
||||
}
|
||||
|
||||
return (void*)fopen (fileName.toUTF8(), mode);
|
||||
}
|
||||
|
||||
void juce_fileClose (void* handle) throw()
|
||||
{
|
||||
if (handle != 0)
|
||||
fclose ((FILE*) handle);
|
||||
}
|
||||
|
||||
int juce_fileRead (void* handle, void* buffer, int size) throw()
|
||||
{
|
||||
if (handle != 0)
|
||||
return fread (buffer, 1, size, (FILE*) handle);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int juce_fileWrite (void* handle, const void* buffer, int size) throw()
|
||||
{
|
||||
if (handle != 0)
|
||||
return fwrite (buffer, 1, size, (FILE*) handle);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int64 juce_fileSetPosition (void* handle, int64 pos) throw()
|
||||
{
|
||||
if (handle != 0 && fseek ((FILE*) handle, (long) pos, SEEK_SET) == 0)
|
||||
return pos;
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
int64 juce_fileGetPosition (void* handle) throw()
|
||||
{
|
||||
if (handle != 0)
|
||||
return ftell ((FILE*) handle);
|
||||
else
|
||||
return -1;
|
||||
}
|
||||
|
||||
void juce_fileFlush (void* handle) throw()
|
||||
{
|
||||
if (handle != 0)
|
||||
fflush ((FILE*) handle);
|
||||
}
|
||||
|
||||
const StringArray juce_getFileSystemRoots() throw()
|
||||
{
|
||||
StringArray s;
|
||||
|
|
@ -294,28 +160,7 @@ const StringArray juce_getFileSystemRoots() throw()
|
|||
return s;
|
||||
}
|
||||
|
||||
const String juce_getVolumeLabel (const String& filenameOnVolume,
|
||||
int& volumeSerialNumber) throw()
|
||||
{
|
||||
// There is no equivalent on Linux
|
||||
volumeSerialNumber = 0;
|
||||
return String::empty;
|
||||
}
|
||||
|
||||
int64 File::getBytesFreeOnVolume() const throw()
|
||||
{
|
||||
struct statfs buf;
|
||||
int64 free_space = 0;
|
||||
|
||||
if (statfs (getFullPathName().toUTF8(), &buf) == 0)
|
||||
{
|
||||
// Note: this returns space available to non-super user
|
||||
free_space = (int64) buf.f_bsize * (int64) buf.f_bavail;
|
||||
}
|
||||
|
||||
return free_space;
|
||||
}
|
||||
|
||||
//==============================================================================
|
||||
bool File::isOnCDRomDrive() const throw()
|
||||
{
|
||||
struct statfs buf;
|
||||
|
|
@ -353,7 +198,6 @@ bool File::isOnHardDisk() const throw()
|
|||
return true;
|
||||
}
|
||||
|
||||
|
||||
//==============================================================================
|
||||
const File File::getSpecialLocation (const SpecialLocationType type)
|
||||
{
|
||||
|
|
@ -439,10 +283,6 @@ bool File::setAsCurrentWorkingDirectory() const throw()
|
|||
return chdir (getFullPathName().toUTF8()) == 0;
|
||||
}
|
||||
|
||||
//==============================================================================
|
||||
const tchar File::separator = T('/');
|
||||
const tchar* File::separatorString = T("/");
|
||||
|
||||
//==============================================================================
|
||||
struct FindFileStruct
|
||||
{
|
||||
|
|
|
|||
|
|
@ -40,12 +40,17 @@ BEGIN_JUCE_NAMESPACE
|
|||
|
||||
#include "../../../src/juce_core/threads/juce_CriticalSection.h"
|
||||
#include "../../../src/juce_core/threads/juce_WaitableEvent.h"
|
||||
#include "../../../src/juce_core/threads/juce_InterProcessLock.h"
|
||||
#include "../../../src/juce_core/threads/juce_Thread.h"
|
||||
#include "../../../src/juce_core/threads/juce_Process.h"
|
||||
#include "../../../src/juce_core/io/files/juce_File.h"
|
||||
#include "../../../src/juce_core/basics/juce_SystemStats.h"
|
||||
|
||||
//==============================================================================
|
||||
/*
|
||||
Note that a lot of methods that you'd expect to find in this file actually
|
||||
live in juce_posix_SharedCode.cpp!
|
||||
*/
|
||||
|
||||
#ifndef CPU_ISSET
|
||||
#undef SUPPORT_AFFINITIES
|
||||
#endif
|
||||
|
|
@ -169,143 +174,6 @@ void Thread::yield() throw()
|
|||
sched_yield();
|
||||
}
|
||||
|
||||
void JUCE_CALLTYPE Thread::sleep (int millisecs) throw()
|
||||
{
|
||||
struct timespec time;
|
||||
time.tv_sec = millisecs / 1000;
|
||||
time.tv_nsec = (millisecs % 1000) * 1000000;
|
||||
nanosleep (&time, 0);
|
||||
}
|
||||
|
||||
//==============================================================================
|
||||
CriticalSection::CriticalSection() throw()
|
||||
{
|
||||
pthread_mutexattr_t atts;
|
||||
pthread_mutexattr_init (&atts);
|
||||
pthread_mutexattr_settype (&atts, PTHREAD_MUTEX_RECURSIVE);
|
||||
pthread_mutex_init (&internal, &atts);
|
||||
}
|
||||
|
||||
CriticalSection::~CriticalSection() throw()
|
||||
{
|
||||
pthread_mutex_destroy (&internal);
|
||||
}
|
||||
|
||||
void CriticalSection::enter() const throw()
|
||||
{
|
||||
pthread_mutex_lock (&internal);
|
||||
}
|
||||
|
||||
bool CriticalSection::tryEnter() const throw()
|
||||
{
|
||||
return pthread_mutex_trylock (&internal) == 0;
|
||||
}
|
||||
|
||||
void CriticalSection::exit() const throw()
|
||||
{
|
||||
pthread_mutex_unlock (&internal);
|
||||
}
|
||||
|
||||
//==============================================================================
|
||||
struct EventStruct
|
||||
{
|
||||
pthread_cond_t condition;
|
||||
pthread_mutex_t mutex;
|
||||
bool triggered;
|
||||
};
|
||||
|
||||
WaitableEvent::WaitableEvent() throw()
|
||||
{
|
||||
EventStruct* const es = new EventStruct();
|
||||
es->triggered = false;
|
||||
|
||||
pthread_cond_init (&es->condition, 0);
|
||||
pthread_mutex_init (&es->mutex, 0);
|
||||
|
||||
internal = es;
|
||||
}
|
||||
|
||||
WaitableEvent::~WaitableEvent() throw()
|
||||
{
|
||||
EventStruct* const es = (EventStruct*)internal;
|
||||
|
||||
pthread_cond_destroy (&es->condition);
|
||||
pthread_mutex_destroy (&es->mutex);
|
||||
|
||||
delete es;
|
||||
}
|
||||
|
||||
bool WaitableEvent::wait (const int timeOutMillisecs) const throw()
|
||||
{
|
||||
EventStruct* const es = (EventStruct*)internal;
|
||||
|
||||
bool ok = true;
|
||||
pthread_mutex_lock (&es->mutex);
|
||||
|
||||
if (! es->triggered)
|
||||
{
|
||||
if (timeOutMillisecs < 0)
|
||||
{
|
||||
pthread_cond_wait (&es->condition, &es->mutex);
|
||||
}
|
||||
else
|
||||
{
|
||||
struct timespec time;
|
||||
struct timeval t;
|
||||
int timeout = 0;
|
||||
|
||||
gettimeofday (&t, 0);
|
||||
|
||||
time.tv_sec = t.tv_sec + (timeOutMillisecs / 1000);
|
||||
time.tv_nsec = (t.tv_usec + ((timeOutMillisecs % 1000) * 1000)) * 1000;
|
||||
|
||||
while (time.tv_nsec >= 1000000000)
|
||||
{
|
||||
time.tv_nsec -= 1000000000;
|
||||
time.tv_sec++;
|
||||
}
|
||||
|
||||
while (! timeout)
|
||||
{
|
||||
timeout = pthread_cond_timedwait (&es->condition, &es->mutex, &time);
|
||||
|
||||
if (! timeout)
|
||||
// Success
|
||||
break;
|
||||
|
||||
if (timeout == EINTR)
|
||||
// Go round again
|
||||
timeout = 0;
|
||||
}
|
||||
}
|
||||
|
||||
ok = es->triggered;
|
||||
}
|
||||
|
||||
es->triggered = false;
|
||||
|
||||
pthread_mutex_unlock (&es->mutex);
|
||||
return ok;
|
||||
}
|
||||
|
||||
void WaitableEvent::signal() const throw()
|
||||
{
|
||||
EventStruct* const es = (EventStruct*)internal;
|
||||
|
||||
pthread_mutex_lock (&es->mutex);
|
||||
es->triggered = true;
|
||||
pthread_cond_broadcast (&es->condition);
|
||||
pthread_mutex_unlock (&es->mutex);
|
||||
}
|
||||
|
||||
void WaitableEvent::reset() const throw()
|
||||
{
|
||||
EventStruct* const es = (EventStruct*)internal;
|
||||
|
||||
pthread_mutex_lock (&es->mutex);
|
||||
es->triggered = false;
|
||||
pthread_mutex_unlock (&es->mutex);
|
||||
}
|
||||
|
||||
//==============================================================================
|
||||
// sets the process to 0=low priority, 1=normal, 2=high, 3=realtime
|
||||
|
|
@ -404,82 +272,4 @@ void* Process::getProcedureEntryPoint (void* libraryHandle, const String& proced
|
|||
#endif
|
||||
|
||||
|
||||
//==============================================================================
|
||||
InterProcessLock::InterProcessLock (const String& name_) throw()
|
||||
: internal (0),
|
||||
name (name_),
|
||||
reentrancyLevel (0)
|
||||
{
|
||||
const File tempDir (File::getSpecialLocation (File::tempDirectory));
|
||||
const File temp (tempDir.getChildFile (name));
|
||||
temp.create();
|
||||
|
||||
internal = (void*) open (temp.getFullPathName().toUTF8(), 'a');
|
||||
}
|
||||
|
||||
InterProcessLock::~InterProcessLock() throw()
|
||||
{
|
||||
while (reentrancyLevel > 0)
|
||||
this->exit();
|
||||
|
||||
#if JUCE_64BIT
|
||||
close ((long long) internal);
|
||||
#else
|
||||
close ((int) internal);
|
||||
#endif
|
||||
}
|
||||
|
||||
bool InterProcessLock::enter (const int timeOutMillisecs) throw()
|
||||
{
|
||||
if (internal == 0)
|
||||
return false;
|
||||
|
||||
if (reentrancyLevel != 0)
|
||||
return true;
|
||||
|
||||
if (timeOutMillisecs <= 0)
|
||||
{
|
||||
if (flock ((long) internal,
|
||||
timeOutMillisecs < 0 ? LOCK_EX
|
||||
: (LOCK_EX | LOCK_NB)) == 0)
|
||||
{
|
||||
++reentrancyLevel;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
const int64 endTime = Time::currentTimeMillis() + timeOutMillisecs;
|
||||
|
||||
for (;;)
|
||||
{
|
||||
if (flock ((long) internal, LOCK_EX | LOCK_NB) == 0)
|
||||
{
|
||||
++reentrancyLevel;
|
||||
return true;
|
||||
}
|
||||
|
||||
if (Time::currentTimeMillis() >= endTime)
|
||||
break;
|
||||
|
||||
Thread::sleep (10);
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
void InterProcessLock::exit() throw()
|
||||
{
|
||||
if (reentrancyLevel > 0 && internal != 0)
|
||||
{
|
||||
--reentrancyLevel;
|
||||
|
||||
const int result = flock ((long) internal, LOCK_UN);
|
||||
(void) result;
|
||||
jassert (result == 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
END_JUCE_NAMESPACE
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue