Make BCatalog threadsafe.
* use a locker to protect the CatalogAddOn-chain against parallel access * rename BCatalog::SetCatalog() to SetTo() and make it a proper initializing function * adjust implementation of BLocaleRoster accordingly
This commit is contained in:
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2003-2010, Haiku, Inc.
|
* Copyright 2003-2012, Haiku, Inc.
|
||||||
* Distributed under the terms of the MIT License.
|
* Distributed under the terms of the MIT License.
|
||||||
*/
|
*/
|
||||||
#ifndef _CATALOG_H_
|
#ifndef _CATALOG_H_
|
||||||
@@ -7,6 +7,7 @@
|
|||||||
|
|
||||||
|
|
||||||
#include <LocaleRoster.h>
|
#include <LocaleRoster.h>
|
||||||
|
#include <Locker.h>
|
||||||
#include <SupportDefs.h>
|
#include <SupportDefs.h>
|
||||||
#include <String.h>
|
#include <String.h>
|
||||||
|
|
||||||
@@ -42,8 +43,9 @@ public:
|
|||||||
status_t GetLanguage(BString* language);
|
status_t GetLanguage(BString* language);
|
||||||
status_t GetFingerprint(uint32* fingerprint);
|
status_t GetFingerprint(uint32* fingerprint);
|
||||||
|
|
||||||
status_t SetCatalog(const entry_ref& catalogOwner,
|
status_t SetTo(const entry_ref& catalogOwner,
|
||||||
uint32 fingerprint);
|
const char* language = NULL,
|
||||||
|
uint32 fingerprint = 0);
|
||||||
|
|
||||||
status_t InitCheck() const;
|
status_t InitCheck() const;
|
||||||
int32 CountItems() const;
|
int32 CountItems() const;
|
||||||
@@ -58,6 +60,7 @@ protected:
|
|||||||
// hide assignment and copy-constructor
|
// hide assignment and copy-constructor
|
||||||
|
|
||||||
BCatalogAddOn* fCatalog;
|
BCatalogAddOn* fCatalog;
|
||||||
|
mutable BLocker fLock;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
friend class BLocale;
|
friend class BLocale;
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2003-2004, Axel Dörfler, [email protected]
|
* Copyright 2003-2004, Axel Dörfler, [email protected]
|
||||||
* Copyright 2003-2004, Oliver Tappe, [email protected]
|
* Copyright 2003-2004,2012, Oliver Tappe, [email protected]
|
||||||
* Distributed under the terms of the MIT License.
|
* Distributed under the terms of the MIT License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@@ -9,6 +9,7 @@
|
|||||||
#include <syslog.h>
|
#include <syslog.h>
|
||||||
|
|
||||||
#include <Application.h>
|
#include <Application.h>
|
||||||
|
#include <Autolock.h>
|
||||||
#include <Locale.h>
|
#include <Locale.h>
|
||||||
#include <MutableLocaleRoster.h>
|
#include <MutableLocaleRoster.h>
|
||||||
#include <Node.h>
|
#include <Node.h>
|
||||||
@@ -21,16 +22,19 @@ using BPrivate::MutableLocaleRoster;
|
|||||||
//#pragma mark - BCatalog
|
//#pragma mark - BCatalog
|
||||||
BCatalog::BCatalog()
|
BCatalog::BCatalog()
|
||||||
:
|
:
|
||||||
fCatalog(NULL)
|
fCatalog(NULL),
|
||||||
|
fLock("Catalog")
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
BCatalog::BCatalog(const entry_ref& catalogOwner, const char* language,
|
BCatalog::BCatalog(const entry_ref& catalogOwner, const char* language,
|
||||||
uint32 fingerprint)
|
uint32 fingerprint)
|
||||||
|
:
|
||||||
|
fCatalog(NULL),
|
||||||
|
fLock("Catalog")
|
||||||
{
|
{
|
||||||
fCatalog = MutableLocaleRoster::Default()->LoadCatalog(catalogOwner,
|
SetTo(catalogOwner, language, fingerprint);
|
||||||
language, fingerprint);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -44,6 +48,10 @@ const char*
|
|||||||
BCatalog::GetString(const char* string, const char* context,
|
BCatalog::GetString(const char* string, const char* context,
|
||||||
const char* comment)
|
const char* comment)
|
||||||
{
|
{
|
||||||
|
BAutolock lock(&fLock);
|
||||||
|
if (!lock.IsLocked())
|
||||||
|
return string;
|
||||||
|
|
||||||
const char* translated;
|
const char* translated;
|
||||||
for (BCatalogAddOn* cat = fCatalog; cat != NULL; cat = cat->fNext) {
|
for (BCatalogAddOn* cat = fCatalog; cat != NULL; cat = cat->fNext) {
|
||||||
translated = cat->GetString(string, context, comment);
|
translated = cat->GetString(string, context, comment);
|
||||||
@@ -58,6 +66,10 @@ BCatalog::GetString(const char* string, const char* context,
|
|||||||
const char*
|
const char*
|
||||||
BCatalog::GetString(uint32 id)
|
BCatalog::GetString(uint32 id)
|
||||||
{
|
{
|
||||||
|
BAutolock lock(&fLock);
|
||||||
|
if (!lock.IsLocked())
|
||||||
|
return "";
|
||||||
|
|
||||||
const char* translated;
|
const char* translated;
|
||||||
for (BCatalogAddOn* cat = fCatalog; cat != NULL; cat = cat->fNext) {
|
for (BCatalogAddOn* cat = fCatalog; cat != NULL; cat = cat->fNext) {
|
||||||
translated = cat->GetString(id);
|
translated = cat->GetString(id);
|
||||||
@@ -72,6 +84,10 @@ BCatalog::GetString(uint32 id)
|
|||||||
status_t
|
status_t
|
||||||
BCatalog::GetData(const char* name, BMessage* msg)
|
BCatalog::GetData(const char* name, BMessage* msg)
|
||||||
{
|
{
|
||||||
|
BAutolock lock(&fLock);
|
||||||
|
if (!lock.IsLocked())
|
||||||
|
return B_ERROR;
|
||||||
|
|
||||||
if (fCatalog == NULL)
|
if (fCatalog == NULL)
|
||||||
return B_NO_INIT;
|
return B_NO_INIT;
|
||||||
|
|
||||||
@@ -89,6 +105,10 @@ BCatalog::GetData(const char* name, BMessage* msg)
|
|||||||
status_t
|
status_t
|
||||||
BCatalog::GetData(uint32 id, BMessage* msg)
|
BCatalog::GetData(uint32 id, BMessage* msg)
|
||||||
{
|
{
|
||||||
|
BAutolock lock(&fLock);
|
||||||
|
if (!lock.IsLocked())
|
||||||
|
return B_ERROR;
|
||||||
|
|
||||||
if (fCatalog == NULL)
|
if (fCatalog == NULL)
|
||||||
return B_NO_INIT;
|
return B_NO_INIT;
|
||||||
|
|
||||||
@@ -106,6 +126,10 @@ BCatalog::GetData(uint32 id, BMessage* msg)
|
|||||||
status_t
|
status_t
|
||||||
BCatalog::GetSignature(BString* sig)
|
BCatalog::GetSignature(BString* sig)
|
||||||
{
|
{
|
||||||
|
BAutolock lock(&fLock);
|
||||||
|
if (!lock.IsLocked())
|
||||||
|
return B_ERROR;
|
||||||
|
|
||||||
if (sig == NULL)
|
if (sig == NULL)
|
||||||
return B_BAD_VALUE;
|
return B_BAD_VALUE;
|
||||||
|
|
||||||
@@ -121,6 +145,10 @@ BCatalog::GetSignature(BString* sig)
|
|||||||
status_t
|
status_t
|
||||||
BCatalog::GetLanguage(BString* lang)
|
BCatalog::GetLanguage(BString* lang)
|
||||||
{
|
{
|
||||||
|
BAutolock lock(&fLock);
|
||||||
|
if (!lock.IsLocked())
|
||||||
|
return B_ERROR;
|
||||||
|
|
||||||
if (lang == NULL)
|
if (lang == NULL)
|
||||||
return B_BAD_VALUE;
|
return B_BAD_VALUE;
|
||||||
|
|
||||||
@@ -136,6 +164,10 @@ BCatalog::GetLanguage(BString* lang)
|
|||||||
status_t
|
status_t
|
||||||
BCatalog::GetFingerprint(uint32* fp)
|
BCatalog::GetFingerprint(uint32* fp)
|
||||||
{
|
{
|
||||||
|
BAutolock lock(&fLock);
|
||||||
|
if (!lock.IsLocked())
|
||||||
|
return B_ERROR;
|
||||||
|
|
||||||
if (fp == NULL)
|
if (fp == NULL)
|
||||||
return B_BAD_VALUE;
|
return B_BAD_VALUE;
|
||||||
|
|
||||||
@@ -149,13 +181,16 @@ BCatalog::GetFingerprint(uint32* fp)
|
|||||||
|
|
||||||
|
|
||||||
status_t
|
status_t
|
||||||
BCatalog::SetCatalog(const entry_ref& catalogOwner, uint32 fingerprint)
|
BCatalog::SetTo(const entry_ref& catalogOwner, const char* language,
|
||||||
|
uint32 fingerprint)
|
||||||
{
|
{
|
||||||
// This is not thread safe. It is used only in ReadOnlyBootPrompt and should
|
BAutolock lock(&fLock);
|
||||||
// not do harm there, but not sure what to do about it…
|
if (!lock.IsLocked())
|
||||||
|
return B_ERROR;
|
||||||
|
|
||||||
MutableLocaleRoster::Default()->UnloadCatalog(fCatalog);
|
MutableLocaleRoster::Default()->UnloadCatalog(fCatalog);
|
||||||
fCatalog = MutableLocaleRoster::Default()->LoadCatalog(catalogOwner, NULL,
|
fCatalog = MutableLocaleRoster::Default()->LoadCatalog(catalogOwner,
|
||||||
fingerprint);
|
language, fingerprint);
|
||||||
|
|
||||||
return B_OK;
|
return B_OK;
|
||||||
}
|
}
|
||||||
@@ -164,6 +199,10 @@ BCatalog::SetCatalog(const entry_ref& catalogOwner, uint32 fingerprint)
|
|||||||
status_t
|
status_t
|
||||||
BCatalog::InitCheck() const
|
BCatalog::InitCheck() const
|
||||||
{
|
{
|
||||||
|
BAutolock lock(&fLock);
|
||||||
|
if (!lock.IsLocked())
|
||||||
|
return B_ERROR;
|
||||||
|
|
||||||
return fCatalog != NULL ? fCatalog->InitCheck() : B_NO_INIT;
|
return fCatalog != NULL ? fCatalog->InitCheck() : B_NO_INIT;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -171,6 +210,10 @@ BCatalog::InitCheck() const
|
|||||||
int32
|
int32
|
||||||
BCatalog::CountItems() const
|
BCatalog::CountItems() const
|
||||||
{
|
{
|
||||||
|
BAutolock lock(&fLock);
|
||||||
|
if (!lock.IsLocked())
|
||||||
|
return 0;
|
||||||
|
|
||||||
return fCatalog != NULL ? fCatalog->CountItems() : 0;
|
return fCatalog != NULL ? fCatalog->CountItems() : 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -548,8 +548,7 @@ BLocaleRoster::_GetCatalog(BCatalog* catalog, vint32* catalogInitStatus)
|
|||||||
|
|
||||||
// load the catalog for this mimetype and return it to the app
|
// load the catalog for this mimetype and return it to the app
|
||||||
entry_ref ref;
|
entry_ref ref;
|
||||||
BEntry(info.name).GetRef(&ref);
|
if (BEntry(info.name).GetRef(&ref) == B_OK && catalog->SetTo(ref) == B_OK)
|
||||||
catalog->SetCatalog(ref, 0);
|
|
||||||
*catalogInitStatus = true;
|
*catalogInitStatus = true;
|
||||||
|
|
||||||
return catalog;
|
return catalog;
|
||||||
|
|||||||
Reference in New Issue
Block a user