* MultiAudioAddOn::_RecursiveScan() now checks the depth of the recursion,

and bails out early.
* InitCheck() now actually returns an error if something went wrong during
  initialization.
* Cleanup, part III.


git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@24627 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Axel Dörfler
2008-03-28 16:46:05 +00:00
parent d5420ddccc
commit f89d079f4e
4 changed files with 152 additions and 164 deletions
@@ -3,29 +3,28 @@
* Distributed under the terms of the MIT License.
*/
#include <MediaDefs.h>
#include <MediaAddOn.h>
#include <Errors.h>
#include <Node.h>
#include <Mime.h>
#include <StorageDefs.h>
#include <Path.h>
#include <Directory.h>
#include <Entry.h>
#include <FindDirectory.h>
#include "MultiAudioNode.h"
#include "MultiAudioAddOn.h"
#include "MultiAudioDevice.h"
#include <limits.h>
#include <stdio.h>
#include <string.h>
#include <Directory.h>
#include <Entry.h>
#include <FindDirectory.h>
#include <File.h>
#include <Path.h>
#include "debug.h"
#include "MultiAudioNode.h"
#include "MultiAudioDevice.h"
#define MULTI_SAVE
const char* kSettingsName = "Media/multi_audio_settings";
//! instantiation function
extern "C" BMediaAddOn*
@@ -39,42 +38,37 @@ make_media_addon(image_id image)
// #pragma mark -
MultiAudioAddOn::MultiAudioAddOn(image_id image)
: BMediaAddOn(image),
fDevices()
{
CALLED();
fInitStatus = _RecursiveScan("/dev/audio/hmulti/");
if (fInitStatus != B_OK)
return;
_LoadSettings();
fInitStatus = B_OK;
}
MultiAudioAddOn::~MultiAudioAddOn()
{
CALLED();
void *device = NULL;
for (int32 i = 0; (device = fDevices.ItemAt(i)); i++)
delete (MultiAudioDevice *)device;
delete (MultiAudioDevice*)device;
SaveSettings();
_SaveSettings();
}
MultiAudioAddOn::MultiAudioAddOn(image_id image)
: BMediaAddOn(image),
fDevices()
{
CALLED();
fInitCheckStatus = B_NO_INIT;
if (RecursiveScan("/dev/audio/hmulti/") != B_OK)
return;
LoadSettings();
fInitCheckStatus = B_OK;
}
// -------------------------------------------------------- //
// BMediaAddOn impl
// -------------------------------------------------------- //
status_t
MultiAudioAddOn::InitCheck(const char** _failureText)
{
CALLED();
return B_OK;
return fInitStatus;
}
@@ -87,13 +81,13 @@ MultiAudioAddOn::CountFlavors()
status_t
MultiAudioAddOn::GetFlavorAt(int32 n, const flavor_info** _info)
MultiAudioAddOn::GetFlavorAt(int32 index, const flavor_info** _info)
{
CALLED();
if (_info == NULL)
return B_BAD_VALUE;
MultiAudioDevice* device = (MultiAudioDevice*)fDevices.ItemAt(n);
MultiAudioDevice* device = (MultiAudioDevice*)fDevices.ItemAt(index);
if (device == NULL)
return B_BAD_INDEX;
@@ -101,7 +95,7 @@ MultiAudioAddOn::GetFlavorAt(int32 n, const flavor_info** _info)
if (info == NULL)
return B_NO_MEMORY;
MultiAudioNode::GetFlavor(info, n);
MultiAudioNode::GetFlavor(info, index);
info->name = (char*)device->Description().friendly_name;
*_info = info;
@@ -143,34 +137,28 @@ MultiAudioAddOn::InstantiateNodeFor(const flavor_info* info, BMessage* config,
status_t
MultiAudioAddOn::GetConfigurationFor(BMediaNode * your_node, BMessage * into_message)
MultiAudioAddOn::GetConfigurationFor(BMediaNode* _node, BMessage* message)
{
CALLED();
MultiAudioNode* node = dynamic_cast<MultiAudioNode*>(_node);
if (node == NULL)
return B_BAD_TYPE;
#ifdef MULTI_SAVE
if (into_message == 0) {
into_message = new BMessage();
MultiAudioNode * node = dynamic_cast<MultiAudioNode*>(your_node);
if (node == 0) {
fprintf(stderr, "<- B_BAD_TYPE\n");
return B_BAD_TYPE;
}
if (node->GetConfigurationFor(into_message) == B_OK) {
fSettings.AddMessage(your_node->Name(), into_message);
if (message == NULL) {
BMessage settings;
if (node->GetConfigurationFor(&settings) == B_OK) {
fSettings.AddMessage(node->Name(), &settings);
}
return B_OK;
}
#endif
// currently never called by the media kit. Seems it is not implemented.
if (into_message == 0) {
fprintf(stderr, "<- B_BAD_VALUE\n");
return B_BAD_VALUE; // we refuse to crash because you were stupid
}
MultiAudioNode * node = dynamic_cast<MultiAudioNode*>(your_node);
if (node == 0) {
fprintf(stderr, "<- B_BAD_TYPE\n");
return B_BAD_TYPE;
}
return node->GetConfigurationFor(into_message);
if (message == NULL)
return B_BAD_VALUE;
return node->GetConfigurationFor(message);
}
@@ -192,9 +180,11 @@ MultiAudioAddOn::AutoStart(int count, BMediaNode** _node, int32* _internalID,
status_t
MultiAudioAddOn::RecursiveScan(char* rootPath, BEntry* rootEntry)
MultiAudioAddOn::_RecursiveScan(char* rootPath, BEntry* rootEntry, uint32 depth)
{
CALLED();
if (depth > 16)
return B_ERROR;
BDirectory root;
if (rootEntry != NULL)
@@ -207,10 +197,9 @@ MultiAudioAddOn::RecursiveScan(char* rootPath, BEntry* rootEntry)
}
BEntry entry;
while (root.GetNextEntry(&entry) > B_ERROR) {
while (root.GetNextEntry(&entry) == B_OK) {
if (entry.IsDirectory()) {
RecursiveScan(rootPath, &entry);
_RecursiveScan(rootPath, &entry, depth + 1);
} else {
BPath path;
entry.GetPath(&path);
@@ -230,34 +219,37 @@ MultiAudioAddOn::RecursiveScan(char* rootPath, BEntry* rootEntry)
void
MultiAudioAddOn::SaveSettings()
MultiAudioAddOn::_SaveSettings()
{
CALLED();
BPath path;
if (find_directory(B_USER_SETTINGS_DIRECTORY, &path) == B_OK) {
path.Append(SETTINGS_FILE);
BFile file(path.Path(), B_READ_WRITE | B_CREATE_FILE | B_ERASE_FILE);
if (file.InitCheck() == B_OK)
fSettings.Flatten(&file);
}
if (find_directory(B_USER_SETTINGS_DIRECTORY, &path) != B_OK)
return;
path.Append(kSettingsName);
BFile file(path.Path(), B_READ_WRITE | B_CREATE_FILE | B_ERASE_FILE);
if (file.InitCheck() == B_OK)
fSettings.Flatten(&file);
}
void
MultiAudioAddOn::LoadSettings()
MultiAudioAddOn::_LoadSettings()
{
CALLED();
fSettings.MakeEmpty();
BPath path;
if (find_directory(B_USER_SETTINGS_DIRECTORY, &path) == B_OK) {
path.Append(SETTINGS_FILE);
BFile file(path.Path(), B_READ_ONLY);
if ((file.InitCheck() == B_OK) && (fSettings.Unflatten(&file) == B_OK))
{
PRINT_OBJECT(fSettings);
} else {
PRINT(("Error unflattening settings file %s\n", path.Path()));
}
if (find_directory(B_USER_SETTINGS_DIRECTORY, &path) != B_OK)
return;
path.Append(kSettingsName);
BFile file(path.Path(), B_READ_ONLY);
if (file.InitCheck() == B_OK && fSettings.Unflatten(&file) == B_OK) {
PRINT_OBJECT(fSettings);
} else {
PRINT(("Error unflattening settings file %s\n", path.Path()));
}
}
@@ -2,59 +2,47 @@
* Copyright (c) 2002, Jerome Duval ([email protected])
* Distributed under the terms of the MIT License.
*/
#ifndef MULTI_AUDIO_ADDON_H
#define MULTI_AUDIO_ADDON_H
#ifndef _MULTIAUDIOADDON_H
#define _MULTIAUDIOADDON_H
#include <MediaDefs.h>
#include <MediaAddOn.h>
#include <Message.h>
#define SETTINGS_FILE "Media/multi_audio_settings"
class BEntry;
class MultiAudioAddOn :
public BMediaAddOn
{
public:
virtual ~MultiAudioAddOn(void);
explicit MultiAudioAddOn(image_id image);
/**************************/
/* begin from BMediaAddOn */
public:
virtual status_t InitCheck(
const char ** out_failure_text);
virtual int32 CountFlavors(void);
virtual status_t GetFlavorAt(
int32 n,
const flavor_info ** out_info);
virtual BMediaNode * InstantiateNodeFor(
const flavor_info * info,
BMessage * config,
status_t * out_error);
virtual status_t GetConfigurationFor(
BMediaNode * your_node,
BMessage * into_message);
virtual bool WantsAutoStart(void);
virtual status_t AutoStart(
int in_count,
BMediaNode ** out_node,
int32 * out_internal_id,
bool * out_has_more);
class MultiAudioAddOn : public BMediaAddOn {
public:
MultiAudioAddOn(image_id image);
virtual ~MultiAudioAddOn();
/* end from BMediaAddOn */
/************************/
virtual status_t InitCheck(const char** _failureText);
virtual int32 CountFlavors();
virtual status_t GetFlavorAt(int32 i, const flavor_info** _info);
virtual BMediaNode* InstantiateNodeFor(const flavor_info* info,
BMessage* config, status_t* _error);
virtual status_t GetConfigurationFor(BMediaNode* node,
BMessage* message);
virtual bool WantsAutoStart();
virtual status_t AutoStart(int count, BMediaNode** _node,
int32* _internalID, bool* _hasMore);
private:
status_t RecursiveScan(char* path, BEntry *rootEntry = NULL);
void SaveSettings();
void LoadSettings();
private:
status_t _RecursiveScan(char* path, BEntry* rootEntry = NULL,
uint32 depth = 0);
void _SaveSettings();
void _LoadSettings();
status_t fInitCheckStatus;
BList fDevices;
private:
status_t fInitStatus;
BList fDevices;
BMessage fSettings; // settings loaded from settings directory
BMessage fSettings;
// loaded from settings directory
};
extern "C" _EXPORT BMediaAddOn *make_media_addon(image_id you);
extern "C" BMediaAddOn* make_media_addon(image_id you);
#endif /* _MULTIAUDIOADDON_H */
#endif // MULTI_AUDIO_ADDON_H
@@ -7,26 +7,52 @@
#include "MultiAudioNode.h"
#if 0
#include <Entry.h>
#include <File.h>
#include <FileInterface.h>
#endif
#include <stdio.h>
#include <string.h>
#include <Buffer.h>
#include <BufferGroup.h>
#include <ParameterWeb.h>
#include "MultiAudioUtility.h"
#ifdef DEBUG
# define PRINTING
#endif
#include "debug.h"
#include <stdio.h>
#include <string.h>
class node_input {
public:
node_input(media_input& input, media_format format);
~node_input();
const char * multi_string[] = {
int32 fChannelId;
media_input fInput;
media_format fPreferredFormat;
media_format fFormat;
uint32 fBufferCycle;
multi_buffer_info fOldBufferInfo;
BBuffer* fBuffer;
};
class node_output {
public:
node_output(media_output& output, media_format format);
~node_output();
int32 fChannelId;
media_output fOutput;
media_format fPreferredFormat;
media_format fFormat;
BBufferGroup* fBufferGroup;
bool fOutputEnabled;
uint64 fSamplesSent;
volatile uint32 fBufferCycle;
multi_buffer_info fOldBufferInfo;
};
const char* kMultiControlString[] = {
"NAME IS ATTACHED",
"Output", "Input", "Setup", "Tone Control", "Extended Setup", "Enhanced Setup", "Master",
"Beep", "Phone", "Mic", "Line", "CD", "Video", "Aux", "Wave", "Gain", "Level", "Volume",
@@ -35,7 +61,7 @@ const char * multi_string[] = {
};
node_input::node_input(media_input &input, media_format format)
node_input::node_input(media_input& input, media_format format)
{
CALLED();
fInput = input;
@@ -44,14 +70,20 @@ node_input::node_input(media_input &input, media_format format)
fBuffer = NULL;
}
node_input::~node_input()
{
CALLED();
}
node_output::node_output(media_output &output, media_format format)
: fBufferGroup(NULL),
fOutputEnabled(true)
// #pragma mark -
node_output::node_output(media_output& output, media_format format)
:
fBufferGroup(NULL),
fOutputEnabled(true)
{
CALLED();
fOutput = output;
@@ -59,12 +91,16 @@ node_output::node_output(media_output &output, media_format format)
fBufferCycle = 1;
}
node_output::~node_output()
{
CALLED();
}
// #pragma mark -
MultiAudioNode::MultiAudioNode(BMediaAddOn* addon, const char* name,
MultiAudioDevice* device, int32 internalID, BMessage* config)
: BMediaNode(name), BBufferConsumer(B_MEDIA_RAW_AUDIO),
@@ -1292,7 +1328,7 @@ const char*
MultiAudioNode::_GetControlName(multi_mix_control& control)
{
if (control.string != S_null)
return multi_string[control.string];
return kMultiControlString[control.string];
return control.name;
}
@@ -22,37 +22,9 @@
class BDiscreteParameter;
class BParameterGroup;
class node_input;
class node_output;
class node_input {
public:
node_input(media_input& input, media_format format);
~node_input();
int32 fChannelId;
media_input fInput;
media_format fPreferredFormat;
media_format fFormat;
uint32 fBufferCycle;
multi_buffer_info fOldBufferInfo;
BBuffer* fBuffer;
};
class node_output {
public:
node_output(media_output& output, media_format format);
~node_output();
int32 fChannelId;
media_output fOutput;
media_format fPreferredFormat;
media_format fFormat;
BBufferGroup* fBufferGroup;
bool fOutputEnabled;
uint64 fSamplesSent;
volatile uint32 fBufferCycle;
multi_buffer_info fOldBufferInfo;
};
class MultiAudioNode : public BBufferConsumer, public BBufferProducer,
public BTimeSource, public BMediaEventLooper, public BControllable {