Code from Philippe Houdoin old machine :)

Fixed code style (not the PPP part)
Updated it with the current Network Pref.
the PPP add-on don't work.
This should work as much as the Network Pref does today.

git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@33155 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Fredrik Modeen
2009-09-16 17:12:22 +00:00
parent 68710d6a76
commit 6046fd9511
68 changed files with 6381 additions and 1047 deletions
@@ -1,57 +0,0 @@
#include "BoneyardAddOn.h"
_EXPORT void boneyard_do_save() {}
_EXPORT void boneyard_do_revert() {}
BYDataEntry::BYDataEntry(const char *name, const char *value, const char *comment)
{
m_name = (char *) name;
m_value = (char *) value;
m_comment = (char *) comment;
}
BYDataEntry::~BYDataEntry() {}
const char * BYDataEntry::Name() { return m_name; }
const char * BYDataEntry::Value() { return m_value; }
const char * BYDataEntry::Comment() { return m_comment; }
void BYDataEntry::SetValue(char *value) { m_value = value; }
void BYDataEntry::SetComment(char *comment) { m_comment = comment; }
void BYDataEntry::_ReservedDataEntry1() {}
void BYDataEntry::_ReservedDataEntry2() {}
BYAddon::BYAddon() {}
BYAddon::~BYAddon() {}
BView * BYAddon::CreateView(BRect *bounds) { return NULL; }
void BYAddon::Revert() {}
void BYAddon::Save() {}
const char *BYAddon::Name() { return "noname"; }
const char *BYAddon::Section() { return "noname"; }
const char *BYAddon::Description() { return "noname"; }
const BList *BYAddon::FileList() { return NULL; }
int BYAddon::Importance() { return 10; }
const BList *BYAddon::ObtainSectionData() { return NULL; } // get all BYDataEntrys for my section.
const char *BYAddon::GetValue(const char *name) { return ""; } // get a value from your section.
void BYAddon::SetValue(const char *name,const char *data) {} // set a value in your section.
void BYAddon::ClearValue(const char *name) {} // remove an entry from your section.
void BYAddon::ClearSectionData() {} // remove all entries from your section.
bool BYAddon::IsDirty() { return false; } // query dirty status
void BYAddon::SetDirty(bool _dirty) {} // set dirty status
const BList *BYAddon::GetAddonList() { return NULL; } // get all add-ons in the cradle.
void BYAddon::_ReservedAddon1() {}
void BYAddon::_ReservedAddon2() {}
void BYAddon::_ReservedAddon3() {}
void BYAddon::_ReservedAddon4() {}
void BYAddon::_ReservedAddon5() {}
void BYAddon::_ReservedAddon6() {}
void BYAddon::_ReservedAddon7() {}
void BYAddon::_ReservedAddon8() {}
// void BYAddon::GetAddonList();
void save_config();
-105
View File
@@ -1,105 +0,0 @@
//******************************************************************************
//
// File: bone_byaddon.h
//
// Description: Addon API for the BONE configuration preference.
//
// Copyright 2000, Be Incorporated, All Rights Reserved.
//
//******************************************************************************
#ifndef H_BONE_BYADDON
#define H_BONE_BYADDON
#include <List.h>
#include <View.h>
class BYDataEntry {
public:
BYDataEntry(const char *name,const char *value,const char *ccomment = NULL);
virtual ~BYDataEntry();
const char *Name();
const char *Value();
const char *Comment();
void SetValue(char *value);
void SetComment(char *comment);
private:
virtual void _ReservedDataEntry1();
virtual void _ReservedDataEntry2();
char *m_name,*m_value,*m_comment;
uint32 _reserved[2];
};
// Common importance values used by BYAddon
#define BY_IMP_IDENTITY 200 // priority of the "Identity" tab
#define BY_IMP_INTERFACES 190 // priority of the "Interfaces" tab
#define BY_IMP_HIGH 150 // put the tab up front
#define BY_IMP_PPP 140 // priority of the "Dial-Up" (PPP) tab
#define BY_IMP_NORMAL 100 // anywhere is fine
#define BY_IMP_SERVICES 90 // priority of the "Services" tab
#define BY_IMP_PROFILES 10 // priority of the "Profiles" tab
#define BY_IMP_LOW 0 // put near the back
class BYAddon {
public:
BYAddon();
virtual ~BYAddon();
// Perform actions
virtual BView *CreateView(BRect *bounds); // return config view
virtual void Revert(); // Revert to settings on disk
virtual void Save(); // Save changes to disk
// status/info
virtual const char *Name(); // name of addon (for tab)
virtual const char *Section(); // section name (for network.conf)
virtual const char *Description(); // description of section
virtual const BList *FileList(); // list of files used for configuration
virtual int Importance(); // sort order in tab list.
// For data collection/management
const BList *ObtainSectionData(); // get all BYDataEntrys for my section.
const char *GetValue(const char *name); // get a value from your section.
void SetValue(const char *name,const char *data); // set a value in your section.
void ClearValue(const char *name); // remove an entry from your section.
void ClearSectionData(); // remove all entries from your section.
bool IsDirty(); // query dirty status
void SetDirty(bool _dirty = true); // set dirty status
const BList *GetAddonList(); // get all add-ons in the cradle.
private:
virtual void _ReservedAddon1();
virtual void _ReservedAddon2();
virtual void _ReservedAddon3();
virtual void _ReservedAddon4();
virtual void _ReservedAddon5();
virtual void _ReservedAddon6();
virtual void _ReservedAddon7();
virtual void _ReservedAddon8();
bool is_dirty;
int32 _reserved[16];
};
extern "C" {
typedef BYAddon *(*by_instantiate_func)(void);
#if defined (__POWERPC__)
#define BONE_EXPORT __declspec(dllexport)
#else
#define BONE_EXPORT
#endif
BONE_EXPORT BYAddon *instantiate(void);
extern void boneyard_do_save();
extern void boneyard_do_revert();
}
#endif
@@ -0,0 +1,70 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/dirent.h>
#include <sys/stat.h>
#include <String.h>
#include <ListView.h>
#include <ListItem.h>
#include <ScrollView.h>
#include <Box.h>
#include <Button.h>
#include <Bitmap.h>
#include <Alert.h>
#include <NetworkSetupAddOn.h>
#include "DialUpView.h"
class AddOn : public NetworkSetupAddOn
{
public:
AddOn(image_id addon_image);
~AddOn();
const char * Name();
BView * CreateView(BRect *bounds);
};
NetworkSetupAddOn * get_nth_addon(image_id image, int index)
{
if (index == 0)
return new AddOn(image);
return NULL;
}
// #pragma mark -
AddOn::AddOn(image_id image)
: NetworkSetupAddOn(image)
{
}
AddOn::~AddOn()
{
}
const char * AddOn::Name()
{
return "DialUp";
}
BView * AddOn::CreateView(BRect *bounds)
{
BRect r = *bounds;
if (r.Width() < 200 || r.Height() < 400)
r.Set(0, 0, 200, 400);
BView *view = new DialUpView(r);
*bounds = view->Bounds();
return view;
}
@@ -0,0 +1,268 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2003-2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
//-----------------------------------------------------------------------
// ConnectionOptionsAddon saves the loaded settings.
// ConnectionOptionsView saves the current settings.
//-----------------------------------------------------------------------
#include "ConnectionOptionsAddon.h"
#include "MessageDriverSettingsUtils.h"
#include <PPPDefs.h>
#include <settings_tools.h>
// message constants
static const uint32 kMsgUpdateControls = 'UCTL';
// labels
#ifdef LANG_GERMAN
static const char *kLabelConnectionOptions = "Optionen";
static const char *kLabelDialOnDemand = "Automatisch Verbinden Bei Zugriff Auf "
"Internet";
static const char *kLabelAskBeforeDialing = "Vor Dem Verbinden Fragen";
static const char *kLabelAutoRedial = "Verbindung Automatisch Wiederherstellen";
#else
static const char *kLabelConnectionOptions = "Options";
static const char *kLabelDialOnDemand = "Connect Automatically When Needed";
static const char *kLabelAskBeforeDialing = "Ask Before Dialing";
static const char *kLabelAutoRedial = "Redial Automatically";
#endif
ConnectionOptionsAddon::ConnectionOptionsAddon(BMessage *addons)
: DialUpAddon(addons),
fSettings(NULL),
fProfile(NULL),
fConnectionOptionsView(NULL)
{
}
ConnectionOptionsAddon::~ConnectionOptionsAddon()
{
}
bool
ConnectionOptionsAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
{
fIsNew = isNew;
fDoesDialOnDemand = fAskBeforeDialing = fDoesAutoRedial = false;
fSettings = settings;
fProfile = profile;
if(fConnectionOptionsView)
fConnectionOptionsView->Reload();
// reset all views (empty settings)
if(!settings || !profile || isNew)
return true;
BMessage parameter;
int32 index = 0;
const char *value;
if(FindMessageParameter(PPP_DIAL_ON_DEMAND_KEY, *fSettings, &parameter, &index)
&& parameter.FindString(MDSU_VALUES, &value) == B_OK) {
if(get_boolean_value(value, false))
fDoesDialOnDemand = true;
parameter.AddBool(MDSU_VALID, true);
fSettings->ReplaceMessage(MDSU_PARAMETERS, index, &parameter);
}
index = 0;
if(FindMessageParameter(PPP_ASK_BEFORE_DIALING_KEY, *fSettings, &parameter, &index)
&& parameter.FindString(MDSU_VALUES, &value) == B_OK) {
if(get_boolean_value(value, false))
fAskBeforeDialing = true;
parameter.AddBool(MDSU_VALID, true);
fSettings->ReplaceMessage(MDSU_PARAMETERS, index, &parameter);
}
index = 0;
if(FindMessageParameter(PPP_AUTO_REDIAL_KEY, *fSettings, &parameter, &index)
&& parameter.FindString(MDSU_VALUES, &value) == B_OK) {
if(get_boolean_value(value, false))
fDoesAutoRedial = true;
parameter.AddBool(MDSU_VALID, true);
fSettings->ReplaceMessage(MDSU_PARAMETERS, index, &parameter);
}
if(fConnectionOptionsView)
fConnectionOptionsView->Reload();
// reload new settings
return true;
}
void
ConnectionOptionsAddon::IsModified(bool *settings, bool *profile) const
{
*settings = *profile = false;
if(!fSettings || !fConnectionOptionsView)
return;
*settings = DoesDialOnDemand() != fConnectionOptionsView->DoesDialOnDemand()
|| AskBeforeDialing() != fConnectionOptionsView->AskBeforeDialing()
|| DoesAutoRedial() != fConnectionOptionsView->DoesAutoRedial();
}
bool
ConnectionOptionsAddon::SaveSettings(BMessage *settings, BMessage *profile, bool saveTemporary)
{
if(!fSettings || !settings)
return false;
BMessage parameter;
if(fConnectionOptionsView->DoesDialOnDemand()) {
parameter.MakeEmpty();
parameter.AddString(MDSU_NAME, PPP_DIAL_ON_DEMAND_KEY);
parameter.AddString(MDSU_VALUES, "enabled");
settings->AddMessage(MDSU_PARAMETERS, &parameter);
if(fConnectionOptionsView->AskBeforeDialing()) {
parameter.MakeEmpty();
parameter.AddString(MDSU_NAME, PPP_ASK_BEFORE_DIALING_KEY);
parameter.AddString(MDSU_VALUES, "enabled");
settings->AddMessage(MDSU_PARAMETERS, &parameter);
}
}
if(fConnectionOptionsView->DoesAutoRedial()) {
parameter.MakeEmpty();
parameter.AddString(MDSU_NAME, PPP_AUTO_REDIAL_KEY);
parameter.AddString(MDSU_VALUES, "enabled");
settings->AddMessage(MDSU_PARAMETERS, &parameter);
}
return true;
}
bool
ConnectionOptionsAddon::GetPreferredSize(float *width, float *height) const
{
BRect rect;
if(Addons()->FindRect(DUN_TAB_VIEW_RECT, &rect) != B_OK)
rect.Set(0, 0, 200, 300);
// set default values
if(width)
*width = rect.Width();
if(height)
*height = rect.Height();
return true;
}
BView*
ConnectionOptionsAddon::CreateView(BPoint leftTop)
{
if(!fConnectionOptionsView) {
BRect rect;
Addons()->FindRect(DUN_TAB_VIEW_RECT, &rect);
fConnectionOptionsView = new ConnectionOptionsView(this, rect);
fConnectionOptionsView->Reload();
}
fConnectionOptionsView->MoveTo(leftTop);
return fConnectionOptionsView;
}
ConnectionOptionsView::ConnectionOptionsView(ConnectionOptionsAddon *addon, BRect frame)
: BView(frame, kLabelConnectionOptions, B_FOLLOW_NONE, 0),
fAddon(addon)
{
BRect rect = Bounds();
rect.InsetBy(10, 10);
rect.bottom = rect.top + 15;
fDialOnDemand = new BCheckBox(rect, "DialOnDemand", kLabelDialOnDemand,
new BMessage(kMsgUpdateControls));
rect.top = rect.bottom + 3;
rect.bottom = rect.top + 15;
rect.left += 20;
fAskBeforeDialing = new BCheckBox(rect, "AskBeforeDialing", kLabelAskBeforeDialing,
NULL);
rect.left -= 20;
rect.top = rect.bottom + 20;
rect.bottom = rect.top + 15;
fAutoRedial = new BCheckBox(rect, "AutoRedial", kLabelAutoRedial, NULL);
AddChild(fDialOnDemand);
AddChild(fAskBeforeDialing);
AddChild(fAutoRedial);
}
void
ConnectionOptionsView::Reload()
{
fDialOnDemand->SetValue(Addon()->DoesDialOnDemand() || Addon()->IsNew());
// this is enabled by default
fAskBeforeDialing->SetValue(Addon()->AskBeforeDialing());
fAutoRedial->SetValue(Addon()->DoesAutoRedial());
if(!Addon()->Settings())
return;
UpdateControls();
}
void
ConnectionOptionsView::AttachedToWindow()
{
SetViewColor(Parent()->ViewColor());
fDialOnDemand->SetTarget(this);
}
void
ConnectionOptionsView::MessageReceived(BMessage *message)
{
switch(message->what) {
case kMsgUpdateControls:
UpdateControls();
break;
default:
BView::MessageReceived(message);
}
}
void
ConnectionOptionsView::UpdateControls()
{
fAskBeforeDialing->SetEnabled(fDialOnDemand->Value());
fAskBeforeDialing->SetValue(fDialOnDemand->Value());
}
@@ -0,0 +1,104 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2003-2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
//-----------------------------------------------------------------------
// ConnectionOptionsAddon saves the loaded settings.
// ConnectionOptionsView saves the current settings.
//-----------------------------------------------------------------------
#ifndef _CONNECTION_OPTIONS_ADDON__H
#define _CONNECTION_OPTIONS_ADDON__H
#include <DialUpAddon.h>
#include <CheckBox.h>
#include <RadioButton.h>
class ConnectionOptionsView;
class ConnectionOptionsAddon : public DialUpAddon {
public:
ConnectionOptionsAddon(BMessage *addons);
virtual ~ConnectionOptionsAddon();
bool IsNew() const
{ return fIsNew; }
bool DoesDialOnDemand() const
{ return fDoesDialOnDemand; }
bool AskBeforeDialing() const
{ return fAskBeforeDialing; }
bool DoesAutoRedial() const
{ return fDoesAutoRedial; }
BMessage *Settings() const
{ return fSettings; }
BMessage *Profile() const
{ return fProfile; }
virtual int32 Position() const
{ return 50; }
virtual bool LoadSettings(BMessage *settings, BMessage *profile, bool isNew);
virtual void IsModified(bool *settings, bool *profile) const;
virtual bool SaveSettings(BMessage *settings, BMessage *profile,
bool saveTemporary);
virtual bool GetPreferredSize(float *width, float *height) const;
virtual BView *CreateView(BPoint leftTop);
private:
bool fIsNew;
bool fDoesDialOnDemand, fAskBeforeDialing, fDoesAutoRedial;
BMessage *fSettings, *fProfile;
// saves last settings state
ConnectionOptionsView *fConnectionOptionsView;
};
class ConnectionOptionsView : public BView {
public:
ConnectionOptionsView(ConnectionOptionsAddon *addon, BRect frame);
ConnectionOptionsAddon *Addon() const
{ return fAddon; }
void Reload();
bool DoesDialOnDemand() const
{ return fDialOnDemand->Value(); }
bool AskBeforeDialing() const
{ return fAskBeforeDialing->Value(); }
bool DoesAutoRedial() const
{ return fAutoRedial->Value(); }
virtual void AttachedToWindow();
virtual void MessageReceived(BMessage *message);
private:
void UpdateControls();
private:
ConnectionOptionsAddon *fAddon;
BCheckBox *fDialOnDemand, *fAskBeforeDialing, *fAutoRedial;
};
#endif
@@ -0,0 +1,34 @@
--------------------------------------------------------------------------------------
Notes for add-on developers:
--------------------------------------------------------------------------------------
All add-ons must add a "Valid" boolean value to every recognized parameter. The preflet will check if all values were recognized and if not it will ask the user if he wants to edit the interface anyway...
--------------------------------------------------------------------------------------
Add-on registration:
--------------------------------------------------------------------------------------
Tabs and Protocols (protocols are tabs):
DUN_TAB_ADDON_TYPE : pointer to DialUpAddon object
Authenticators:
DUN_AUTHENTICATOR_ADDON_TYPE : BMessage with the following entries:
{
"KernelModule" : string
"TechnicalName" : string
"FriendlyName" : string
"Position" : int32
}
Devices:
DUN_DEVICE_ADDON_TYPE : pointer to DialUpAddon object
Addons that must be deleted:
DUN_DELETE_ON_QUIT : pointer to DialUpAddon object - this will be deleted when the preflet quits
(you should register all your addons here, too)
--------------------------------------------------------------------------------------
Additional data in the BMessage object for add-ons:
--------------------------------------------------------------------------------------
DUN_MESSENGER : BMessenger - This messenger can be used to send messages to the preflet
DUN_TAB_VIEW_RECT : BRect - This rect should be used for tabs
DUN_DEVICE_VIEW_WIDTH : float - Maximum width a device add-on's view may have
@@ -0,0 +1,141 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
/*! \class DialUpAddon
\brief Base class for DialUpPreflet add-ons.
Dial-Up add-ons must export the following function: \n
bool register(BMessage *addons) \n
You should add your DialUpAddon object to the given BMessage. \n
\n
Most add-ons are simple pointers to a DialUpAddon object. \n
\n
Note for tab-addons: The BView object is deleted AFTER the DialUpAddon (except you
remove and delete it in the DialUpAddon destructor).
*/
#ifndef _DIAL_UP_ADDON__H
#define _DIAL_UP_ADDON__H
#include <SupportDefs.h>
#include <Point.h>
#define DUN_MAXIMUM_PRIORITY 50
// add-on types
#define DUN_TAB_ADDON_TYPE "Tab"
#define DUN_AUTHENTICATOR_ADDON_TYPE "Authenticator"
#define DUN_DEVICE_ADDON_TYPE "Device"
#define DUN_PROTOCOL_ADDON_TYPE "Protocol"
// other information contained in the add-ons BMessage object
#define DUN_DELETE_ON_QUIT "DeleteMe"
// the DialUpAddon objects in this list will be deleted when the preflet quits
#define DUN_MESSENGER "Messenger"
#define DUN_TAB_VIEW_RECT "TabViewRect"
#define DUN_DEVICE_VIEW_WIDTH "DeviceViewWidth"
class DialUpAddon {
friend class DialUpView;
public:
//! Constructor. The BMessage is the one passed to the \c register() function.
DialUpAddon(BMessage *addons) : fAddons(addons) {}
//! Destructor. Does nothing.
virtual ~DialUpAddon() {}
//! Returns the BMessage object holding all add-ons.
BMessage *Addons() const
{ return fAddons; }
//! Returns a name readable by humans without much technical knowledge.
virtual const char *FriendlyName() const
{ return NULL; }
//! Returns the technical name of this module.
virtual const char *TechnicalName() const
{ return NULL; }
//! Returns the name of the associated kernel module or \c NULL.
virtual const char *KernelModuleName() const
{ return NULL; }
//! Mostly used by tabs to describe where they should appear.
virtual int32 Position() const
{ return -1; }
//! Allows setting an order in which modules are asked to add the settings.
virtual int32 Priority() const
{ return 0; }
/*! \brief Load the given settings and profile.
\param isNew Specifies if this is a newly created interface.
\return \c true if loading was successful or \c false otherwise.
*/
virtual bool LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
{ return false; }
/*! \brief Returns if this module has a temporary profile.
A temporary profile is never stored on the hard-disk, but only passed
to the interface on connection. This can include passwords, for example.
*/
virtual bool HasTemporaryProfile() const
{ return false; }
//! Are the settings or the profile modified?
virtual void IsModified(bool *settings, bool *profile) const
{ *settings = *profile = false; }
/*! \brief Save the given settings and profile.
\param saveTemporary Specifies if the temporary profile should be written.
\return \c true if saving was successful or \c false otherwise.
*/
virtual bool SaveSettings(BMessage *settings, BMessage *profile,
bool saveTemporary)
{ return false; }
/*! \brief Get the preferred view size.
\return \c false if this module does not export a BView object.
*/
virtual bool GetPreferredSize(float *width, float *height) const
{ return false; }
/*! \brief Returns the module's BView object.
\param leftTop Specifies the view's left-top coordinates.
*/
virtual BView *CreateView(BPoint leftTop)
{ return NULL; }
private:
virtual void _Reserved1() {}
virtual void _Reserved2() {}
virtual void _Reserved3() {}
virtual void _Reserved4() {}
private:
BMessage *fAddons;
int32 _reserved[7];
};
#endif
@@ -0,0 +1,77 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2003-2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
#include <Application.h>
#include <Window.h>
#include "InterfaceUtils.h"
#include "DialUpView.h"
static const char *kSignature = "application/x-vnd.haiku.dial-up-preflet";
class DialUpApplication : public BApplication {
public:
DialUpApplication();
};
class DialUpWindow : public BWindow {
public:
DialUpWindow(BRect frame);
virtual bool QuitRequested()
{ be_app->PostMessage(B_QUIT_REQUESTED); return true; }
};
int main()
{
new DialUpApplication();
be_app->Run();
delete be_app;
return 0;
}
DialUpApplication::DialUpApplication()
: BApplication(kSignature)
{
BRect rect(150, 50, 450, 435);
DialUpWindow *window = new DialUpWindow(rect);
window->MoveTo(center_on_screen(rect, window));
window->Show();
}
DialUpWindow::DialUpWindow(BRect frame)
: BWindow(frame, "DialUp", B_TITLED_WINDOW, B_NOT_RESIZABLE | B_NOT_ZOOMABLE)
{
DialUpView *view = new DialUpView(Bounds());
AddChild(view);
}
@@ -0,0 +1,37 @@
/*
DialUpPreflet.rdef
*/
resource app_signature "application/x-vnd.haiku.dial-up-preflet";
/* BEOS:APP_FLAGS :
00000000 = SINGLE LAUNCH
00000001 = MULTIPLE LAUNCH
00000002 = EXCLUSIVE LAUNCH
00000004 = BACKGROUND APP + SINGLE LAUNCH
00000005 = BACKGROUND APP + MULTIPLE LAUNCH
00000006 = BACKGROUND APP + EXCLUSIVE LAUNCH
00000008 = ARGV_ONLY + SINGLE LAUNCH
00000009 = ARGV_ONLY + MULTIPLE LAUNCH
0000000A = ARGV_ONLY + EXCLUSIVE LAUNCH
0000000C = ARGV_ONLY + BACKGROUND APP + SINGLE LAUNCH
0000000D = ARGV_ONLY + BACKGROUND APP + MULTIPLE LAUNCH
0000000E = ARGV_ONLY + BACKGROUND APP + EXCLUSIVE LAUNCH
*/
resource app_flags 0x00000000;
resource app_version {
major = 0,
middle = 1,
minor = 0,
/* 0 = development 1 = alpha 2 = beta
3 = gamma 4 = golden master 5 = final */
variety = 0,
internal = 0,
short_info = "DialUpPreflet",
long_info = "PPP interface configuration tool."
};
@@ -0,0 +1,906 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2003-2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
#include "DialUpView.h"
#include "DialUpAddon.h"
#include <cstring>
#include "InterfaceUtils.h"
#include "MessageDriverSettingsUtils.h"
#include "TextRequestDialog.h"
// built-in add-ons
#include "ConnectionOptionsAddon.h"
#include "GeneralAddon.h"
#include "IPCPAddon.h"
#include "PPPoEAddon.h"
#include <PPPInterface.h>
#include <settings_tools.h>
#include <TemplateList.h>
#include <Application.h>
#include <Alert.h>
#include <Button.h>
#include <MenuField.h>
#include <MenuItem.h>
#include <Messenger.h>
#include <PopUpMenu.h>
#include <StringView.h>
#include <TabView.h>
#include <Directory.h>
#include <Entry.h>
#include <File.h>
#include <Path.h>
// message constants
static const uint32 kMsgCreateNew = 'NEWI';
static const uint32 kMsgFinishCreateNew = 'FNEW';
static const uint32 kMsgDeleteCurrent = 'DELI';
static const uint32 kMsgSelectInterface = 'SELI';
static const uint32 kMsgConnectButton = 'CONI';
// labels
#ifdef LANG_GERMAN
static const char *kLabelInterface = "Verbindung: ";
static const char *kLabelInterfaceName = "Verbindungs-Name: ";
static const char *kLabelCreateNewInterface = "Neue Verbindung Erstellen";
static const char *kLabelCreateNew = "Neu...";
static const char *kLabelDeleteCurrent = "Auswahl Löschen";
static const char *kLabelConnect = "Verbinden";
static const char *kLabelDisconnect = "Trennen";
static const char *kLabelOK = "OK";
#else
static const char *kLabelInterface = "Interface: ";
static const char *kLabelInterfaceName = "Interface Name: ";
static const char *kLabelCreateNewInterface = "Create New Interface";
static const char *kLabelCreateNew = "Create New...";
static const char *kLabelDeleteCurrent = "Delete Current";
static const char *kLabelConnect = "Connect";
static const char *kLabelDisconnect = "Disconnect";
static const char *kLabelOK = "OK";
#endif
// connection status strings
#ifdef LANG_GERMAN
static const char *kTextConnecting = "Verbinde...";
static const char *kTextConnectionEstablished = "Verbindung hergestellt.";
static const char *kTextNotConnected = "Nicht verbunden.";
static const char *kTextDeviceUpFailed = "Konnte Verbindung nicht aufbauen.";
static const char *kTextAuthenticating = "Authentifizierung...";
static const char *kTextAuthenticationFailed = "Authentifizierung fehlgeschlagen!";
static const char *kTextConnectionLost = "Verbindung verloren!";
static const char *kTextCreationError = "Fehler beim Initialisieren!";
static const char *kTextNoInterfacesFound = "Bitte erstellen Sie eine neue "
"Verbindung.";
static const char *kTextChooseInterfaceName = "Bitte denken Sie sich einen neuen "
"Namen für diese Verbindung aus.";
#else
static const char *kTextConnecting = "Connecting...";
static const char *kTextConnectionEstablished = "Connection established.";
static const char *kTextNotConnected = "Not connected.";
static const char *kTextDeviceUpFailed = "Failed to connect.";
static const char *kTextAuthenticating = "Authenticating...";
static const char *kTextAuthenticationFailed = "Authentication failed!";
static const char *kTextConnectionLost = "Connection lost!";
static const char *kTextCreationError = "Error creating interface!";
static const char *kTextNoInterfacesFound = "Please create a new interface...";
static const char *kTextChooseInterfaceName = "Please choose a new name for this "
"interface.";
#endif
// error strings for alerts
#ifdef LANG_GERMAN
static const char *kErrorTitle = "Fehler";
static const char *kErrorNoPPPStack = "Fehler: Kein Zugriff auf den PPP Stack!";
static const char *kErrorInterfaceExists = "Fehler: Eine Verbindung mit diesem Namen "
"existiert bereits!";
static const char *kErrorLoadingFailed = "Fehler: Konfiguration ist fehlerhaft! Die "
"Einstellungen werden zurückgesetzt.";
static const char *kErrorSavingFailed = "Fehler: Speichern der Einstellungen ist "
"fehlgeschlagen!";
#else
static const char *kErrorTitle = "Error";
static const char *kErrorNoPPPStack = "Error: Could not access the PPP stack!";
static const char *kErrorInterfaceExists = "Error: An interface with this name "
"already exists!";
static const char *kErrorLoadingFailed = "Error: Failed loading interface! The "
"current settings will be deleted.";
static const char *kErrorSavingFailed = "Error: Failed saving interface settings!";
#endif
static
status_t
up_down_thread(void *data)
{
static_cast<DialUpView*>(data)->UpDownThread();
return B_OK;
}
DialUpView::DialUpView(BRect frame)
: BView(frame, "DialUpView", B_FOLLOW_ALL, 0),
fListener(this),
fUpDownThread(-1),
fDriverSettings(NULL),
fCurrentItem(NULL),
fWatching(PPP_UNDEFINED_INTERFACE_ID),
fKeepLabel(false)
{
BRect bounds = Bounds();
// for caching
SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR));
// add messenger to us so add-ons can contact us
BMessenger messenger(this);
fAddons.AddMessenger(DUN_MESSENGER, messenger);
// create pop-up with all interfaces and "New..."/"Delete current" items
fInterfaceMenu = new BPopUpMenu(kLabelCreateNew);
BRect rect = bounds;
rect.InsetBy(5, 5);
rect.bottom = rect.top + 20;
fMenuField = new BMenuField(rect, "Interfaces", kLabelInterface, fInterfaceMenu);
fMenuField->SetDivider(StringWidth(fMenuField->Label()) + 5);
rect.top = rect.bottom + 10;
rect.bottom = bounds.bottom
- 20 // height of bottom controls
- 20; // space for bottom controls
fTabView = new BTabView(rect, "TabView", B_WIDTH_FROM_LABEL);
BRect tabViewRect(fTabView->Bounds());
tabViewRect.bottom -= fTabView->TabHeight();
fAddons.AddRect(DUN_TAB_VIEW_RECT, tabViewRect);
BRect tmpRect(rect);
tmpRect.top += (tmpRect.Height() - 15) / 2;
tmpRect.bottom = tmpRect.top + 15;
fStringView = new BStringView(tmpRect, "NoInterfacesFound",
kTextNoInterfacesFound);
fStringView->SetAlignment(B_ALIGN_CENTER);
fStringView->Hide();
tmpRect.top = tmpRect.bottom + 10;
tmpRect.bottom = tmpRect.top + 25;
fCreateNewButton = new BButton(tmpRect, "CreateNewButton",
kLabelCreateNewInterface, new BMessage(kMsgCreateNew));
fCreateNewButton->ResizeToPreferred();
tmpRect.left = (rect.Width() - fCreateNewButton->Bounds().Width()) / 2 + rect.left;
fCreateNewButton->MoveTo(tmpRect.left, tmpRect.top);
fCreateNewButton->Hide();
rect.top = rect.bottom + 15;
rect.bottom = rect.top + 15;
rect.right = rect.left + 200;
fStatusView = new BStringView(rect, "StatusView", kTextNotConnected, B_FOLLOW_BOTTOM);
rect.InsetBy(0, -5);
rect.left = rect.right + 5;
rect.right = bounds.right - 5;
fConnectButton = new BButton(rect, "ConnectButton", kLabelConnect,
new BMessage(kMsgConnectButton), B_FOLLOW_BOTTOM);
AddChild(fMenuField);
AddChild(fTabView);
AddChild(fStringView);
AddChild(fCreateNewButton);
AddChild(fStatusView);
AddChild(fConnectButton);
// initialize
LoadInterfaces();
LoadAddons();
CreateTabs();
fCurrentItem = NULL;
// reset, otherwise SelectInterface will not load the settings
SelectInterface(0);
UpdateControls();
}
DialUpView::~DialUpView()
{
SaveSettingsToFile();
int32 tmp;
wait_for_thread(fUpDownThread, &tmp);
// free known add-on types (these should free their known add-on types, etc.)
DialUpAddon *addon;
for(int32 index = 0;
fAddons.FindPointer(DUN_DELETE_ON_QUIT, index,
reinterpret_cast<void**>(&addon)) == B_OK;
index++)
delete addon;
}
void
DialUpView::AttachedToWindow()
{
fInterfaceMenu->SetTargetForItems(this);
fCreateNewButton->SetTarget(this);
fConnectButton->SetTarget(this);
if(fListener.InitCheck() != B_OK) {
(new BAlert(kErrorTitle, kErrorNoPPPStack, kLabelOK,
NULL, NULL, B_WIDTH_AS_USUAL, B_WARNING_ALERT))->Go(NULL);
fConnectButton->Hide();
}
}
void
DialUpView::MessageReceived(BMessage *message)
{
switch(message->what) {
case PPP_REPORT_MESSAGE:
HandleReportMessage(message);
break;
// -------------------------------------------------
case kMsgCreateNew: {
(new TextRequestDialog(kLabelCreateNewInterface, kTextChooseInterfaceName,
kLabelInterfaceName))->Go(
new BInvoker(new BMessage(kMsgFinishCreateNew), this));
} break;
case kMsgFinishCreateNew: {
int32 which;
message->FindInt32("which", &which);
const char *name = message->FindString("text");
if(which == 1 && name && strlen(name) > 0)
AddInterface(name, true);
if(fCurrentItem)
fCurrentItem->SetMarked(true);
} break;
// -------------------------------------------------
case kMsgDeleteCurrent: {
if(!fCurrentItem)
return;
fInterfaceMenu->RemoveItem(fCurrentItem);
BDirectory settings, profile;
GetPPPDirectories(&settings, &profile);
BEntry entry;
settings.FindEntry(fCurrentItem->Label(), &entry);
entry.Remove();
profile.FindEntry(fCurrentItem->Label(), &entry);
entry.Remove();
delete fCurrentItem;
fCurrentItem = NULL;
BMenuItem *marked = fInterfaceMenu->FindMarked();
if(marked)
marked->SetMarked(false);
UpdateControls();
SelectInterface(0);
// this stops watching the deleted interface
} break;
case kMsgSelectInterface: {
int32 index;
message->FindInt32("index", &index);
SelectInterface(index);
} break;
case kMsgConnectButton: {
if(!fCurrentItem || fUpDownThread != -1)
return;
fUpDownThread = spawn_thread(up_down_thread, "up_down_thread",
B_NORMAL_PRIORITY, this);
resume_thread(fUpDownThread);
} break;
default:
BView::MessageReceived(message);
}
}
bool
DialUpView::SelectInterfaceNamed(const char *name)
{
BMenuItem *item = fInterfaceMenu->FindItem(name);
int32 index = fInterfaceMenu->IndexOf(item);
if(!item || index >= CountInterfaces())
return false;
SelectInterface(index);
return true;
}
bool
DialUpView::NeedsRequest() const
{
return fGeneralAddon ? fGeneralAddon->NeedsAuthenticationRequest() : false;
}
BView*
DialUpView::AuthenticationView() const
{
return fGeneralAddon ? fGeneralAddon->AuthenticationView() : NULL;
}
BView*
DialUpView::StatusView() const
{
return fStatusView;
}
BView*
DialUpView::ConnectButton() const
{
return fConnectButton;
}
bool
DialUpView::LoadSettings(bool isNew)
{
fSettings.MakeEmpty();
fProfile.MakeEmpty();
BMessage *settingsPointer = fCurrentItem ? &fSettings : NULL,
*profilePointer = fCurrentItem ? &fProfile : NULL;
if(fCurrentItem && !isNew) {
BString name("pppidf/");
name << fCurrentItem->Label();
if(!ReadMessageDriverSettings(name.String(), &fSettings))
return false;
name = "pppidf/profile/";
name << fCurrentItem->Label();
if(!ReadMessageDriverSettings(name.String(), &fProfile))
profilePointer = settingsPointer;
}
DialUpAddon *addon;
for(int32 index = 0; fAddons.FindPointer(DUN_TAB_ADDON_TYPE, index,
reinterpret_cast<void**>(&addon)) == B_OK; index++) {
if(!addon)
continue;
if(!addon->LoadSettings(settingsPointer, profilePointer, isNew))
return false;
}
// TODO: check if settings are valid
return true;
}
void
DialUpView::IsModified(bool *settings, bool *profile)
{
*settings = *profile = false;
bool addonSettingsChanged, addonProfileChanged;
// for current addon
DialUpAddon *addon;
for(int32 index = 0; fAddons.FindPointer(DUN_TAB_ADDON_TYPE, index,
reinterpret_cast<void**>(&addon)) == B_OK; index++) {
if(!addon)
continue;
addon->IsModified(&addonSettingsChanged, &addonProfileChanged);
if(addonSettingsChanged)
*settings = true;
if(addonProfileChanged)
*profile = true;
}
}
bool
DialUpView::SaveSettings(BMessage *settings, BMessage *profile, bool saveTemporary)
{
if(!fCurrentItem || !settings || !profile)
return false;
DialUpAddon *addon;
TemplateList<DialUpAddon*> addons;
for(int32 index = 0;
fAddons.FindPointer(DUN_TAB_ADDON_TYPE, index,
reinterpret_cast<void**>(&addon)) == B_OK; index++) {
if(!addon)
continue;
int32 insertIndex = 0;
for(; insertIndex < addons.CountItems(); insertIndex++)
if(addons.ItemAt(insertIndex)->Priority() <= addon->Priority())
break;
addons.AddItem(addon, insertIndex);
}
settings->AddInt32("Interface", static_cast<int32>(fWatching));
if(fCurrentItem)
settings->AddString("InterfaceName", fCurrentItem->Label());
for(int32 index = 0; index < addons.CountItems(); index++)
if(!addons.ItemAt(index)->SaveSettings(settings, profile, saveTemporary))
return false;
return true;
}
bool
DialUpView::SaveSettingsToFile()
{
bool settingsChanged, profileChanged;
IsModified(&settingsChanged, &profileChanged);
if(!settingsChanged && !profileChanged)
return true;
BMessage settings, profile;
if(!SaveSettings(&settings, &profile, false))
return false;
BDirectory settingsDirectory;
BDirectory profileDirectory;
GetPPPDirectories(&settingsDirectory, &profileDirectory);
if(settingsDirectory.InitCheck() != B_OK || profileDirectory.InitCheck() != B_OK)
return false;
BFile file;
if(settingsChanged) {
settingsDirectory.CreateFile(fCurrentItem->Label(), &file);
WriteMessageDriverSettings(file, settings);
}
if(profileChanged) {
profileDirectory.CreateFile(fCurrentItem->Label(), &file);
WriteMessageDriverSettings(file, profile);
}
return true;
}
void
DialUpView::UpDownThread()
{
SaveSettingsToFile();
BMessage settings, profile;
SaveSettings(&settings, &profile, true);
// save temporary profile
driver_settings *temporaryProfile = MessageToDriverSettings(profile);
PPPInterface interface;
if(fWatching == PPP_UNDEFINED_INTERFACE_ID) {
interface = fListener.Manager().InterfaceWithName(fCurrentItem->Label());
if(interface.InitCheck() != B_OK)
interface = fListener.Manager().CreateInterfaceWithName(
fCurrentItem->Label(), temporaryProfile);
} else {
interface = fWatching;
interface.SetProfile(temporaryProfile);
}
free_driver_settings(temporaryProfile);
if(interface.InitCheck() != B_OK) {
Window()->Lock();
fStatusView->SetText(kTextCreationError);
Window()->Unlock();
return;
}
ppp_interface_info_t info;
interface.GetInterfaceInfo(&info);
if(info.info.phase == PPP_DOWN_PHASE)
interface.Up();
else
interface.Down();
fUpDownThread = -1;
}
void
DialUpView::GetPPPDirectories(BDirectory *settingsDirectory,
BDirectory *profileDirectory) const
{
if(settingsDirectory) {
BDirectory settings(PPP_INTERFACE_SETTINGS_PATH);
if(settings.InitCheck() != B_OK) {
create_directory(PPP_INTERFACE_SETTINGS_PATH, 0750);
settings.SetTo(PPP_INTERFACE_SETTINGS_PATH);
}
*settingsDirectory = settings;
}
if(profileDirectory) {
BDirectory profile(PPP_INTERFACE_SETTINGS_PATH "/profile");
if(profile.InitCheck() != B_OK) {
create_directory(PPP_INTERFACE_SETTINGS_PATH "/profile", 0750);
profile.SetTo(PPP_INTERFACE_SETTINGS_PATH "/profile");
}
*profileDirectory = profile;
}
}
void
DialUpView::HandleReportMessage(BMessage *message)
{
thread_id sender;
message->FindInt32("sender", &sender);
send_data(sender, B_OK, NULL, 0);
if(!fCurrentItem)
return;
ppp_interface_id id;
if(message->FindInt32("interface", reinterpret_cast<int32*>(&id)) != B_OK
|| (fWatching != PPP_UNDEFINED_INTERFACE_ID && id != fWatching))
return;
int32 type, code;
message->FindInt32("type", &type);
message->FindInt32("code", &code);
if(type == PPP_MANAGER_REPORT && code == PPP_REPORT_INTERFACE_CREATED) {
PPPInterface interface(id);
if(interface.InitCheck() != B_OK)
return;
ppp_interface_info_t info;
interface.GetInterfaceInfo(&info);
if(strcasecmp(info.info.name, fCurrentItem->Label()))
return;
WatchInterface(id);
} else if(type == PPP_CONNECTION_REPORT) {
if(fWatching == PPP_UNDEFINED_INTERFACE_ID)
return;
UpdateStatus(code);
} else if(type == PPP_DESTRUCTION_REPORT) {
if(fWatching == PPP_UNDEFINED_INTERFACE_ID)
return;
WatchInterface(fListener.Manager().InterfaceWithName(fCurrentItem->Label()));
}
}
void
DialUpView::CreateTabs()
{
// create tabs for all registered and valid tab add-ons
DialUpAddon *addon;
BView *target;
float width, height;
TemplateList<DialUpAddon*> addons;
for(int32 index = 0;
fAddons.FindPointer(DUN_TAB_ADDON_TYPE, index,
reinterpret_cast<void**>(&addon)) == B_OK;
index++) {
if(!addon || addon->Position() < 0)
continue;
int32 insertIndex = 0;
for(; insertIndex < addons.CountItems(); insertIndex++)
if(addons.ItemAt(insertIndex)->Position() > addon->Position())
break;
addons.AddItem(addon, insertIndex);
}
for(int32 index = 0; index < addons.CountItems(); index++) {
addon = addons.ItemAt(index);
if(!addon->GetPreferredSize(&width, &height))
continue;
target = addon->CreateView(BPoint(0, 0));
if(!target)
continue;
fTabView->AddTab(target, NULL);
}
}
void
DialUpView::UpdateStatus(int32 code)
{
switch(code) {
case PPP_REPORT_UP_ABORTED:
case PPP_REPORT_DEVICE_UP_FAILED:
case PPP_REPORT_LOCAL_AUTHENTICATION_FAILED:
case PPP_REPORT_PEER_AUTHENTICATION_FAILED:
case PPP_REPORT_DOWN_SUCCESSFUL:
case PPP_REPORT_CONNECTION_LOST: {
fConnectButton->SetLabel(kLabelConnect);
} break;
default:
fConnectButton->SetLabel(kLabelDisconnect);
}
// maybe the status string must not be changed (codes that set fKeepLabel to false
// should still be handled)
if(fKeepLabel && code != PPP_REPORT_GOING_UP && code != PPP_REPORT_UP_SUCCESSFUL)
return;
if(fListener.InitCheck() != B_OK) {
fStatusView->SetText(kErrorNoPPPStack);
return;
}
// only errors should set fKeepLabel to true
switch(code) {
case PPP_REPORT_GOING_UP:
fKeepLabel = false;
fStatusView->SetText(kTextConnecting);
break;
case PPP_REPORT_UP_SUCCESSFUL:
fKeepLabel = false;
fStatusView->SetText(kTextConnectionEstablished);
break;
case PPP_REPORT_UP_ABORTED:
case PPP_REPORT_DOWN_SUCCESSFUL:
fStatusView->SetText(kTextNotConnected);
break;
case PPP_REPORT_DEVICE_UP_FAILED:
fKeepLabel = true;
fStatusView->SetText(kTextDeviceUpFailed);
break;
case PPP_REPORT_LOCAL_AUTHENTICATION_REQUESTED:
case PPP_REPORT_PEER_AUTHENTICATION_REQUESTED:
fStatusView->SetText(kTextAuthenticating);
break;
case PPP_REPORT_LOCAL_AUTHENTICATION_FAILED:
case PPP_REPORT_PEER_AUTHENTICATION_FAILED:
fKeepLabel = true;
fStatusView->SetText(kTextAuthenticationFailed);
break;
case PPP_REPORT_CONNECTION_LOST:
fKeepLabel = true;
fStatusView->SetText(kTextConnectionLost);
break;
}
}
void
DialUpView::WatchInterface(ppp_interface_id ID)
{
// This method can be used to update the interface's connection status.
if(fWatching != ID) {
fListener.StopWatchingInterfaces();
if(ID == PPP_UNDEFINED_INTERFACE_ID || fListener.WatchInterface(ID))
fWatching = ID;
}
// update status
PPPInterface interface(fWatching);
if(interface.InitCheck() != B_OK) {
UpdateStatus(PPP_REPORT_DOWN_SUCCESSFUL);
return;
}
ppp_interface_info_t info;
interface.GetInterfaceInfo(&info);
// transform phase into status
switch(info.info.phase) {
case PPP_DOWN_PHASE:
UpdateStatus(PPP_REPORT_DOWN_SUCCESSFUL);
break;
case PPP_TERMINATION_PHASE:
break;
case PPP_ESTABLISHED_PHASE:
UpdateStatus(PPP_REPORT_UP_SUCCESSFUL);
break;
default:
UpdateStatus(PPP_REPORT_GOING_UP);
}
}
void
DialUpView::LoadInterfaces()
{
fInterfaceMenu->AddSeparatorItem();
fInterfaceMenu->AddItem(new BMenuItem(kLabelCreateNewInterface,
new BMessage(kMsgCreateNew)));
fDeleterItem = new BMenuItem(kLabelDeleteCurrent,
new BMessage(kMsgDeleteCurrent));
fInterfaceMenu->AddItem(fDeleterItem);
BDirectory settingsDirectory;
BEntry entry;
BPath path;
GetPPPDirectories(&settingsDirectory, NULL);
while(settingsDirectory.GetNextEntry(&entry) == B_OK) {
if(entry.IsFile()) {
entry.GetPath(&path);
AddInterface(path.Leaf(), true);
}
}
}
void
DialUpView::LoadAddons()
{
// Load integrated add-ons:
// "Connection Options" tab
ConnectionOptionsAddon *connectionOptionsAddon =
new ConnectionOptionsAddon(&fAddons);
fAddons.AddPointer(DUN_TAB_ADDON_TYPE, connectionOptionsAddon);
fAddons.AddPointer(DUN_DELETE_ON_QUIT, connectionOptionsAddon);
// "General" tab
GeneralAddon *fGeneralAddon = new GeneralAddon(&fAddons);
fAddons.AddPointer(DUN_TAB_ADDON_TYPE, fGeneralAddon);
fAddons.AddPointer(DUN_DELETE_ON_QUIT, fGeneralAddon);
/*
// "IPCP" protocol
IPCPAddon *ipcpAddon = new IPCPAddon(&fAddons);
fAddons.AddPointer(DUN_TAB_ADDON_TYPE, ipcpAddon);
fAddons.AddPointer(DUN_DELETE_ON_QUIT, ipcpAddon);
// "PPPoE" device
PPPoEAddon *pppoeAddon = new PPPoEAddon(&fAddons);
fAddons.AddPointer(DUN_DEVICE_ADDON_TYPE, pppoeAddon);
fAddons.AddPointer(DUN_DELETE_ON_QUIT, pppoeAddon);
*/
// "PAP" authenticator
BMessage addon;
#ifdef LANG_GERMAN
addon.AddString("FriendlyName", "Unverschlüsselt");
#else
addon.AddString("FriendlyName", "Plain-text Authentication");
#endif
addon.AddString("TechnicalName", "PAP");
addon.AddString("KernelModuleName", "pap");
fAddons.AddMessage(DUN_AUTHENTICATOR_ADDON_TYPE, &addon);
// addon.MakeEmpty(); // for next authenticator
// TODO:
// load all add-ons from the add-ons folder
}
void
DialUpView::AddInterface(const char *name, bool isNew)
{
if(fInterfaceMenu->FindItem(name)) {
(new BAlert(kErrorTitle, kErrorInterfaceExists, kLabelOK,
NULL, NULL, B_WIDTH_AS_USUAL, B_WARNING_ALERT))->Go(NULL);
return;
}
BMenuItem *item = new BMenuItem(name, new BMessage(kMsgSelectInterface));
item->SetTarget(this);
int32 index = FindNextMenuInsertionIndex(fInterfaceMenu, name);
if(index > CountInterfaces())
index = CountInterfaces();
fInterfaceMenu->AddItem(item, index);
UpdateControls();
item->SetMarked(true);
SelectInterface(index, isNew);
}
void
DialUpView::SelectInterface(int32 index, bool isNew)
{
BMenuItem *item = fInterfaceMenu->FindMarked();
if(fCurrentItem && item == fCurrentItem)
return;
if(fCurrentItem && !SaveSettingsToFile())
(new BAlert(kErrorTitle, kErrorSavingFailed, kLabelOK,
NULL, NULL, B_WIDTH_AS_USUAL, B_WARNING_ALERT))->Go(NULL);
if(index >= CountInterfaces() || index < 0) {
if(CountInterfaces() > 0)
SelectInterface(0);
else {
fCurrentItem = NULL;
WatchInterface(PPP_UNDEFINED_INTERFACE_ID);
}
} else {
fCurrentItem = fInterfaceMenu->ItemAt(index);
if(!fCurrentItem) {
SelectInterface(0);
return;
}
fCurrentItem->SetMarked(true);
fDeleterItem->SetEnabled(true);
WatchInterface(fListener.Manager().InterfaceWithName(fCurrentItem->Label()));
}
if(!fCurrentItem)
LoadSettings(false);
// tell modules to unload all settings
else if(!isNew && !LoadSettings(false)) {
(new BAlert(kErrorTitle, kErrorLoadingFailed, kLabelOK,
NULL, NULL, B_WIDTH_AS_USUAL, B_WARNING_ALERT))->Go(NULL);
LoadSettings(true);
} else if(isNew && !LoadSettings(true))
(new BAlert(kErrorTitle, kErrorLoadingFailed, kLabelOK,
NULL, NULL, B_WIDTH_AS_USUAL, B_WARNING_ALERT))->Go(NULL);
}
int32
DialUpView::CountInterfaces() const
{
return fInterfaceMenu->CountItems() - 3;
}
void
DialUpView::UpdateControls()
{
if(fTabView->IsHidden() && CountInterfaces() > 0) {
fInterfaceMenu->SetLabelFromMarked(true);
fStringView->Hide();
fCreateNewButton->Hide();
fTabView->Show();
fConnectButton->SetEnabled(true);
} else if(!fTabView->IsHidden() && CountInterfaces() == 0) {
fDeleterItem->SetEnabled(false);
fInterfaceMenu->SetRadioMode(false);
fInterfaceMenu->Superitem()->SetLabel(kLabelCreateNew);
fTabView->Hide();
fStringView->Show();
fCreateNewButton->Show();
fConnectButton->SetEnabled(false);
}
}
@@ -0,0 +1,97 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2003-2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
#ifndef _DIAL_UP_VIEW__H
#define _DIAL_UP_VIEW__H
#include <Message.h>
#include <View.h>
#include <PPPInterfaceListener.h>
class GeneralAddon;
class DialUpView : public BView {
public:
DialUpView(BRect frame);
virtual ~DialUpView();
virtual void AttachedToWindow();
virtual void MessageReceived(BMessage *message);
void UpDownThread();
// used by ppp_up application
bool SelectInterfaceNamed(const char *name);
bool NeedsRequest() const;
BView *AuthenticationView() const;
BView *StatusView() const;
BView *ConnectButton() const;
bool SaveSettings(BMessage *settings, BMessage *profile, bool saveTemporary);
bool SaveSettingsToFile();
private:
void GetPPPDirectories(BDirectory *settingsDirectory,
BDirectory *profileDirectory) const;
void HandleReportMessage(BMessage *message);
void CreateTabs();
void UpdateStatus(int32 code);
void WatchInterface(ppp_interface_id ID);
bool LoadSettings(bool isNew);
void IsModified(bool *settings, bool *profile);
void LoadInterfaces();
void LoadAddons();
void AddInterface(const char *name, bool isNew = false);
void SelectInterface(int32 index, bool isNew = false);
int32 CountInterfaces() const;
void UpdateControls();
private:
PPPInterfaceListener fListener;
thread_id fUpDownThread;
BMessage fAddons, fSettings, fProfile;
driver_settings *fDriverSettings;
BMenuItem *fCurrentItem, *fDeleterItem;
ppp_interface_id fWatching;
GeneralAddon *fGeneralAddon;
bool fKeepLabel;
BStringView *fStatusView;
BButton *fConnectButton, *fCreateNewButton;
BPopUpMenu *fInterfaceMenu;
BMenuField *fMenuField;
BStringView *fStringView;
// shows "No interfaces found..." notice
BTabView *fTabView;
};
#endif
@@ -0,0 +1,718 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2003-2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
//-----------------------------------------------------------------------
// GeneralAddon saves the loaded settings.
// GeneralView saves the current settings.
//-----------------------------------------------------------------------
#include "GeneralAddon.h"
#include "InterfaceUtils.h"
#include "MessageDriverSettingsUtils.h"
#include <stl_algobase.h>
// for max()
#include <Box.h>
#include <Button.h>
#include <MenuField.h>
#include <MenuItem.h>
#include <PopUpMenu.h>
#include <StringView.h>
#include <PPPDefs.h>
// message constants
static const uint32 kMsgSelectDevice = 'SELD';
static const uint32 kMsgSelectAuthenticator = 'SELA';
// labels
#ifdef LANG_GERMAN
static const char *kLabelGeneral = "Allgemein";
static const char *kLabelDevice = "Gerät: ";
static const char *kLabelNoDevicesFound = "Keine Geräte Gefunden!";
static const char *kLabelAuthenticator = "Login: ";
static const char *kLabelNoAuthenticatorsFound = "Keine Login-Methoden gefunden!";
static const char *kLabelName = "Benutzername: ";
static const char *kLabelPassword = "Password: ";
static const char *kLabelSavePassword = "Passwort Speichern";
static const char *kLabelNone = "Ohne";
#else
static const char *kLabelGeneral = "General";
static const char *kLabelDevice = "Device: ";
static const char *kLabelNoDevicesFound = "No Devices Found!";
static const char *kLabelAuthenticator = "Login: ";
static const char *kLabelNoAuthenticatorsFound = "No Authenticators Found!";
static const char *kLabelName = "Username: ";
static const char *kLabelPassword = "Password: ";
static const char *kLabelSavePassword = "Save Password";
static const char *kLabelNone = "None";
#endif
// string constants for information saved in the settings message
static const char *kGeneralTabAuthentication = "Authentication";
static const char *kGeneralTabAuthenticators = "Authenticators";
#define DEFAULT_AUTHENTICATOR "PAP"
// this authenticator is selected by default when creating a new interface
GeneralAddon::GeneralAddon(BMessage *addons)
: DialUpAddon(addons),
fHasPassword(false),
fAuthenticatorsCount(0),
fSettings(NULL),
fProfile(NULL),
fGeneralView(NULL)
{
}
GeneralAddon::~GeneralAddon()
{
}
bool
GeneralAddon::NeedsAuthenticationRequest() const
{
return fGeneralView->AuthenticatorName();
}
DialUpAddon*
GeneralAddon::FindDevice(const BString& moduleName) const
{
DialUpAddon *addon;
for(int32 index = 0; Addons()->FindPointer(DUN_DEVICE_ADDON_TYPE, index,
reinterpret_cast<void**>(&addon)) == B_OK; index++)
if(addon && moduleName == addon->KernelModuleName())
return addon;
return NULL;
}
bool
GeneralAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
{
fIsNew = isNew;
fHasPassword = false;
fDeviceName = fUsername = fPassword = "";
fDeviceAddon = NULL;
fAuthenticatorsCount = 0;
fSettings = settings;
fProfile = profile;
if(fGeneralView)
fGeneralView->Reload();
// reset all views (empty settings)
if(!settings || !profile || isNew)
return true;
if(!LoadDeviceSettings())
return false;
if(!LoadAuthenticationSettings())
return false;
if(fGeneralView)
fGeneralView->Reload();
// reload new settings
return true;
}
bool
GeneralAddon::LoadDeviceSettings()
{
int32 index = 0;
BMessage device;
if(!FindMessageParameter(PPP_DEVICE_KEY, *fSettings, &device, &index))
return false;
// TODO: tell user that device specification is missing
if(device.FindString(MDSU_VALUES, &fDeviceName) != B_OK)
return false;
// TODO: tell user that device specification is missing
device.AddBool(MDSU_VALID, true);
fSettings->ReplaceMessage(MDSU_PARAMETERS, index, &device);
fDeviceAddon = FindDevice(fDeviceName);
if(!fDeviceAddon)
return false;
return fDeviceAddon->LoadSettings(fSettings, fProfile, false);
}
bool
GeneralAddon::LoadAuthenticationSettings()
{
// we only handle the profile (although settings could contain different data)
int32 itemIndex = 0;
BMessage authentication, item;
if(!FindMessageParameter(PPP_AUTHENTICATOR_KEY, *fProfile, &item, &itemIndex))
return true;
// find authenticators (though we load all authenticators, we only use one)
BString name;
for(int32 index = 0; item.FindString(MDSU_VALUES, index, &name) == B_OK; index++) {
BMessage authenticator;
if(!GetAuthenticator(name, &authenticator))
return false;
// fatal error: we do not know how to handle this authenticator
MarkAuthenticatorAsValid(name);
authentication.AddString(kGeneralTabAuthenticators, name);
++fAuthenticatorsCount;
}
fSettings->AddMessage(kGeneralTabAuthentication, &authentication);
bool hasUsername = false;
// a username must be present
// load username and password
BMessage parameter;
int32 parameterIndex = 0;
if(FindMessageParameter("User", item, &parameter, &parameterIndex)
&& parameter.FindString(MDSU_VALUES, &fUsername) == B_OK) {
hasUsername = true;
parameter.AddBool(MDSU_VALID, true);
item.ReplaceMessage(MDSU_PARAMETERS, parameterIndex, &parameter);
}
parameterIndex = 0;
if(FindMessageParameter("Password", item, &parameter, &parameterIndex)
&& parameter.FindString(MDSU_VALUES, &fPassword) == B_OK) {
fHasPassword = true;
parameter.AddBool(MDSU_VALID, true);
item.ReplaceMessage(MDSU_PARAMETERS, parameterIndex, &parameter);
}
// tell DUN whether everything is valid
if(hasUsername)
item.AddBool(MDSU_VALID, true);
fProfile->ReplaceMessage(MDSU_PARAMETERS, itemIndex, &item);
return true;
}
bool
GeneralAddon::HasTemporaryProfile() const
{
return fGeneralView->HasTemporaryProfile();
}
void
GeneralAddon::IsModified(bool *settings, bool *profile) const
{
if(!fSettings) {
*settings = *profile = false;
return;
}
bool deviceSettings, authenticationSettings, deviceProfile, authenticationProfile;
IsDeviceModified(&deviceSettings, &deviceProfile);
IsAuthenticationModified(&authenticationSettings, &authenticationProfile);
*settings = (deviceSettings || authenticationSettings);
*profile = (deviceProfile || authenticationProfile);
}
void
GeneralAddon::IsDeviceModified(bool *settings, bool *profile) const
{
fGeneralView->IsDeviceModified(settings, profile);
}
void
GeneralAddon::IsAuthenticationModified(bool *settings, bool *profile) const
{
// currently we only support selecting one authenticator
if(fAuthenticatorsCount == 0)
*settings = fGeneralView->AuthenticatorName();
else {
BMessage authentication;
if(fSettings->FindMessage(kGeneralTabAuthentication, &authentication) != B_OK) {
*settings = *profile = false;
return;
// error!
}
BString authenticator;
if(authentication.FindString(kGeneralTabAuthenticators,
&authenticator) != B_OK) {
*settings = *profile = false;
return;
// error!
}
*settings = (!fGeneralView->AuthenticatorName()
|| authenticator != fGeneralView->AuthenticatorName());
}
*profile = (*settings || fUsername != fGeneralView->Username()
|| (fPassword != fGeneralView->Password() && fHasPassword)
|| fHasPassword != fGeneralView->DoesSavePassword());
}
bool
GeneralAddon::SaveSettings(BMessage *settings, BMessage *profile, bool saveTemporary)
{
if(!fSettings || !settings || !fGeneralView->DeviceName())
return false;
// TODO: tell user that a device is needed (if we fail because of this)
if(!fGeneralView->DeviceAddon() || !fGeneralView->DeviceAddon()->SaveSettings(
settings, profile, saveTemporary))
return false;
if(fGeneralView->AuthenticatorName()) {
BMessage authenticator;
authenticator.AddString(MDSU_NAME, PPP_AUTHENTICATOR_KEY);
authenticator.AddString(MDSU_VALUES, fGeneralView->AuthenticatorName());
settings->AddMessage(MDSU_PARAMETERS, &authenticator);
BMessage username;
username.AddString(MDSU_NAME, "User");
username.AddString(MDSU_VALUES, fGeneralView->Username());
authenticator.AddMessage(MDSU_PARAMETERS, &username);
if(saveTemporary || fGeneralView->DoesSavePassword()) {
// save password, too
BMessage password;
password.AddString(MDSU_NAME, "Password");
password.AddString(MDSU_VALUES, fGeneralView->Password());
authenticator.AddMessage(MDSU_PARAMETERS, &password);
}
profile->AddMessage(MDSU_PARAMETERS, &authenticator);
}
return true;
}
bool
GeneralAddon::GetPreferredSize(float *width, float *height) const
{
BRect rect;
if(Addons()->FindRect(DUN_TAB_VIEW_RECT, &rect) != B_OK)
rect.Set(0, 0, 200, 300);
// set default values
if(width)
*width = rect.Width();
if(height)
*height = rect.Height();
return true;
}
BView*
GeneralAddon::CreateView(BPoint leftTop)
{
if(!fGeneralView) {
BRect rect;
Addons()->FindRect(DUN_TAB_VIEW_RECT, &rect);
fGeneralView = new GeneralView(this, rect);
fGeneralView->Reload();
}
fGeneralView->MoveTo(leftTop);
return fGeneralView;
}
BView*
GeneralAddon::AuthenticationView() const
{
return fGeneralView ? fGeneralView->AuthenticationView() : NULL;
}
bool
GeneralAddon::GetAuthenticator(const BString& moduleName, BMessage *entry) const
{
if(!entry)
return false;
BString name;
for(int32 index = 0; Addons()->FindMessage(DUN_AUTHENTICATOR_ADDON_TYPE, index,
entry) == B_OK; index++) {
entry->FindString("KernelModuleName", &name);
if(name == moduleName)
return true;
}
return false;
}
bool
GeneralAddon::MarkAuthenticatorAsValid(const BString& moduleName)
{
BMessage authenticator;
int32 index = 0;
BString name;
for(; FindMessageParameter(PPP_AUTHENTICATOR_KEY, *fSettings, &authenticator,
&index); index++) {
authenticator.FindString("KernelModuleName", &name);
if(name == moduleName) {
authenticator.AddBool(MDSU_VALID, true);
fSettings->ReplaceMessage(MDSU_PARAMETERS, index, &authenticator);
return true;
}
}
return false;
}
GeneralView::GeneralView(GeneralAddon *addon, BRect frame)
: BView(frame, kLabelGeneral, B_FOLLOW_NONE, 0),
fAddon(addon)
{
BRect rect = Bounds();
rect.InsetBy(5, 5);
rect.bottom = 100;
fDeviceBox = new BBox(rect, "Device");
Addon()->Addons()->AddFloat(DUN_DEVICE_VIEW_WIDTH,
fDeviceBox->Bounds().Width() - 10);
rect.top = rect.bottom + 10;
rect.bottom = rect.top
+ 25 // space for topmost control
+ 3 * 20 // size of controls
+ 3 * 5; // space beween controls and bottom of box
fAuthenticationBox = new BBox(rect, "Authentication");
fDeviceField = new BMenuField(BRect(5, 0, 250, 20), "Device",
kLabelDevice, new BPopUpMenu(kLabelNoDevicesFound));
fDeviceField->SetDivider(StringWidth(fDeviceField->Label()) + 5);
fDeviceField->Menu()->SetRadioMode(true);
AddDevices();
fDeviceBox->SetLabel(fDeviceField);
fAuthenticatorField = new BMenuField(BRect(5, 0, 250, 20), "Authenticator",
kLabelAuthenticator, new BPopUpMenu(kLabelNoAuthenticatorsFound));
fAuthenticatorField->SetDivider(StringWidth(fAuthenticatorField->Label()) + 5);
fAuthenticatorField->Menu()->SetRadioMode(true);
AddAuthenticators();
fAuthenticationBox->SetLabel(fAuthenticatorField);
rect = fAuthenticationBox->Bounds();
rect.InsetBy(10, 5);
rect.top = 25;
// fAuthenticationView = new BControl(rect, "authenticationView", NULL, NULL,
// B_FOLLOW_NONE, 0);
// BControl automatically sets the view color when attached (we want that)
fAuthenticationView = new BView(rect, "authenticationView", B_FOLLOW_NONE, 0);
fAuthenticationView->SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR));
rect = fAuthenticationView->Bounds();
rect.bottom = rect.top + 20;
fUsername = new BTextControl(rect, "username", kLabelName, NULL, NULL);
rect.top = rect.bottom + 5;
rect.bottom = rect.top + 20;
fPassword = new BTextControl(rect, "password", kLabelPassword, NULL, NULL);
fPassword->TextView()->HideTyping(true);
// set dividers
float width = max(StringWidth(fUsername->Label()),
StringWidth(fPassword->Label()));
fUsername->SetDivider(width + 5);
fPassword->SetDivider(width + 5);
rect.top = rect.bottom + 5;
rect.bottom = rect.top + 20;
fSavePassword = new BCheckBox(rect, "SavePassword", kLabelSavePassword, NULL);
fAuthenticationView->AddChild(fUsername);
fAuthenticationView->AddChild(fPassword);
fAuthenticationView->AddChild(fSavePassword);
fAuthenticationBox->AddChild(fAuthenticationView);
AddChild(fDeviceBox);
AddChild(fAuthenticationBox);
}
GeneralView::~GeneralView()
{
}
void
GeneralView::Reload()
{
fDeviceAddon = NULL;
BMenuItem *item = NULL;
for(int32 index = 0; index < fDeviceField->Menu()->CountItems(); index++) {
item = fDeviceField->Menu()->ItemAt(index);
if(item && item->Message() && item->Message()->FindPointer("Addon",
reinterpret_cast<void**>(&fDeviceAddon)) == B_OK
&& fDeviceAddon == Addon()->DeviceAddon())
break;
}
if(fDeviceAddon && fDeviceAddon == Addon()->DeviceAddon())
item->SetMarked(true);
else if(Addon()->IsNew() && fDeviceField->Menu()->CountItems() > 0) {
item = fDeviceField->Menu()->ItemAt(0);
item->SetMarked(true);
item->Message()->FindPointer("Addon", reinterpret_cast<void**>(&fDeviceAddon));
fDeviceAddon->LoadSettings(Addon()->Settings(), Addon()->Profile(), true);
} else {
fDeviceAddon = NULL;
item = fDeviceField->Menu()->FindMarked();
if(item)
item->SetMarked(false);
}
if(Addon()->CountAuthenticators() > 0) {
BString kernelModule, authenticator;
BMessage authentication;
if(Addon()->Settings()->FindMessage(kGeneralTabAuthentication,
&authentication) == B_OK)
authentication.FindString(kGeneralTabAuthenticators, &authenticator);
BMenu *menu = fAuthenticatorField->Menu();
for(int32 index = 0; index < menu->CountItems(); index++) {
item = menu->ItemAt(index);
if(item && item->Message()
&& item->Message()->FindString("KernelModuleName",
&kernelModule) == B_OK && kernelModule == authenticator) {
item->SetMarked(true);
break;
}
}
} else if(Addon()->IsNew() && fAuthenticatorDefault)
fAuthenticatorDefault->SetMarked(true);
else
fAuthenticatorNone->SetMarked(true);
fUsername->SetText(Addon()->Username());
fPassword->SetText(Addon()->Password());
fSavePassword->SetValue(Addon()->HasPassword());
ReloadDeviceView();
UpdateControls();
}
const char*
GeneralView::DeviceName() const
{
if(fDeviceAddon)
return fDeviceAddon->KernelModuleName();
return NULL;
}
const char*
GeneralView::AuthenticatorName() const
{
BMenuItem *marked = fAuthenticatorField->Menu()->FindMarked();
if(marked && marked != fAuthenticatorNone)
return marked->Message()->FindString("KernelModuleName");
return NULL;
}
void
GeneralView::IsDeviceModified(bool *settings, bool *profile) const
{
if(fDeviceAddon != Addon()->DeviceAddon())
*settings = *profile = true;
else if(fDeviceAddon)
fDeviceAddon->IsModified(settings, profile);
else
*settings = *profile = false;
}
void
GeneralView::AttachedToWindow()
{
SetViewColor(Parent()->ViewColor());
fDeviceField->Menu()->SetTargetForItems(this);
fAuthenticatorField->Menu()->SetTargetForItems(this);
fUsername->SetTarget(this);
fPassword->SetTarget(this);
}
void
GeneralView::MessageReceived(BMessage *message)
{
switch(message->what) {
case kMsgSelectDevice:
if(message->FindPointer("Addon", reinterpret_cast<void**>(&fDeviceAddon))
!= B_OK)
fDeviceAddon = NULL;
else {
if(fDeviceAddon != Addon()->DeviceAddon())
fDeviceAddon->LoadSettings(Addon()->Settings(), Addon()->Profile(),
Addon()->IsNew());
ReloadDeviceView();
}
break;
case kMsgSelectAuthenticator:
UpdateControls();
break;
default:
BView::MessageReceived(message);
}
}
void
GeneralView::ReloadDeviceView()
{
// first remove existing device view(s)
while(fDeviceBox->CountChildren() > 1)
fDeviceBox->RemoveChild(fDeviceBox->ChildAt(1));
if(!fDeviceAddon)
return;
BRect rect(fDeviceBox->Bounds());
float width, height;
if(!fDeviceAddon->GetPreferredSize(&width, &height)) {
width = rect.Width();
height = 50;
}
if(width > rect.Width())
width = rect.Width();
if(height < 10)
height = 10;
// set minimum height
else if(height > 200)
height = 200;
// set maximum height
rect.InsetBy((rect.Width() - width) / 2, 0);
// center horizontally
rect.top = 25;
rect.bottom = rect.top + height;
float deltaY = height + 30 - fDeviceBox->Bounds().Height();
fDeviceBox->ResizeBy(0, deltaY);
fAuthenticationBox->MoveBy(0, deltaY);
BView *deviceView = fDeviceAddon->CreateView(rect.LeftTop());
if(deviceView)
fDeviceBox->AddChild(deviceView);
}
void
GeneralView::UpdateControls()
{
BMenu *menu = fAuthenticatorField->Menu();
int32 index = menu->IndexOf(menu->FindMarked());
if(index < 0)
fAuthenticatorNone->SetMarked(true);
if(index == 0) {
fUsername->SetEnabled(false);
fPassword->SetEnabled(false);
fSavePassword->SetEnabled(false);
} else {
fUsername->SetEnabled(true);
fPassword->SetEnabled(true);
fSavePassword->SetEnabled(true);
}
}
void
GeneralView::AddDevices()
{
AddAddonsToMenu(Addon()->Addons(), fDeviceField->Menu(), DUN_DEVICE_ADDON_TYPE,
kMsgSelectDevice);
}
void
GeneralView::AddAuthenticators()
{
fAuthenticatorDefault = NULL;
fAuthenticatorNone = new BMenuItem(kLabelNone,
new BMessage(kMsgSelectAuthenticator));
fAuthenticatorField->Menu()->AddItem(fAuthenticatorNone);
fAuthenticatorNone->SetMarked(true);
fAuthenticatorField->Menu()->AddSeparatorItem();
BMenuItem *item;
BMessage addon;
for(int32 index = 0;
Addon()->Addons()->FindMessage(DUN_AUTHENTICATOR_ADDON_TYPE, index,
&addon) == B_OK; index++) {
BMessage *message = new BMessage(kMsgSelectAuthenticator);
message->AddString("KernelModuleName", addon.FindString("KernelModuleName"));
BString name, technicalName, friendlyName;
bool hasTechnicalName
= (addon.FindString("TechnicalName", &technicalName) == B_OK);
bool hasFriendlyName
= (addon.FindString("FriendlyName", &friendlyName) == B_OK);
if(hasTechnicalName) {
name << technicalName;
if(hasFriendlyName)
name << " (";
}
if(hasFriendlyName) {
name << friendlyName;
if(hasTechnicalName)
name << ")";
}
int32 insertAt = FindNextMenuInsertionIndex(fAuthenticatorField->Menu(),
name.String(), 2);
item = new BMenuItem(name.String(), message);
if(hasTechnicalName && technicalName == DEFAULT_AUTHENTICATOR)
fAuthenticatorDefault = item;
fAuthenticatorField->Menu()->AddItem(item, insertAt);
}
}
@@ -0,0 +1,157 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2003-2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
//-----------------------------------------------------------------------
// GeneralAddon saves the loaded settings.
// GeneralView saves the current settings.
//-----------------------------------------------------------------------
#ifndef _GENERAL_ADDON__H
#define _GENERAL_ADDON__H
#include <DialUpAddon.h>
#include <CheckBox.h>
#include <String.h>
#include <TextControl.h>
class GeneralView;
class GeneralAddon : public DialUpAddon {
public:
GeneralAddon(BMessage *addons);
virtual ~GeneralAddon();
bool IsNew() const
{ return fIsNew; }
const char *DeviceName() const
{ return fDeviceName.String(); }
const char *Username() const
{ return fUsername.String(); }
const char *Password() const
{ return fPassword.String(); }
bool HasPassword() const
{ return fHasPassword; }
bool NeedsAuthenticationRequest() const;
DialUpAddon *FindDevice(const BString& moduleName) const;
DialUpAddon *DeviceAddon() const
{ return fDeviceAddon; }
int32 CountAuthenticators() const
{ return fAuthenticatorsCount; }
BMessage *Settings() const
{ return fSettings; }
BMessage *Profile() const
{ return fProfile; }
virtual int32 Position() const
{ return 0; }
virtual bool LoadSettings(BMessage *settings, BMessage *profile, bool isNew);
bool LoadDeviceSettings();
bool LoadAuthenticationSettings();
virtual bool HasTemporaryProfile() const;
virtual void IsModified(bool *settings, bool *profile) const;
void IsDeviceModified(bool *settings, bool *profile) const;
void IsAuthenticationModified(bool *settings, bool *profile) const;
virtual bool SaveSettings(BMessage *settings, BMessage *profile,
bool saveTemporary);
virtual bool GetPreferredSize(float *width, float *height) const;
virtual BView *CreateView(BPoint leftTop);
// used by ppp_up application
BView *AuthenticationView() const;
private:
bool GetAuthenticator(const BString& moduleName, BMessage *entry) const;
bool MarkAuthenticatorAsValid(const BString& moduleName);
private:
bool fIsNew, fHasPassword;
BString fDeviceName, fUsername, fPassword;
DialUpAddon *fDeviceAddon;
int32 fAuthenticatorsCount;
BMessage *fSettings, *fProfile;
// saves last settings state
GeneralView *fGeneralView;
};
class GeneralView : public BView {
public:
GeneralView(GeneralAddon *addon, BRect frame);
virtual ~GeneralView();
GeneralAddon *Addon() const
{ return fAddon; }
void Reload();
const char *Username() const
{ return fUsername->Text(); }
const char *Password() const
{ return fPassword->Text(); }
bool DoesSavePassword() const
{ return fSavePassword->Value(); }
bool HasTemporaryProfile() const
{ return !DoesSavePassword() || (fDeviceAddon &&
fDeviceAddon->HasTemporaryProfile()); }
DialUpAddon *DeviceAddon() const
{ return fDeviceAddon; }
const char *DeviceName() const;
const char *AuthenticatorName() const;
void IsDeviceModified(bool *settings, bool *profile) const;
virtual void AttachedToWindow();
virtual void MessageReceived(BMessage *message);
// used by ppp_up application
BView *AuthenticationView() const
{ return fAuthenticationView; }
private:
void ReloadDeviceView();
void UpdateControls();
void AddDevices();
void AddAuthenticators();
private:
GeneralAddon *fAddon;
DialUpAddon *fDeviceAddon;
BBox *fDeviceBox, *fAuthenticationBox;
BView *fAuthenticationView;
BMenuField *fDeviceField, *fAuthenticatorField;
BMenuItem *fAuthenticatorNone, *fAuthenticatorDefault;
BTextControl *fUsername, *fPassword;
BCheckBox *fSavePassword;
};
#endif
@@ -0,0 +1,382 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2003-2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
//-----------------------------------------------------------------------
// IPCPAddon saves the loaded settings.
// IPCPView saves the current settings.
//-----------------------------------------------------------------------
#include "IPCPAddon.h"
#include "MessageDriverSettingsUtils.h"
#include <stl_algobase.h>
// for max()
#include <StringView.h>
#include <PPPDefs.h>
#include <IPCP.h>
// from IPCP addon
// GUI constants
static const uint32 kDefaultButtonWidth = 80;
// message constants
static const uint32 kMsgUpdateControls = 'UCTL';
// labels
#ifdef LANG_GERMAN
static const char *kLabelIPCP = "TCP/IP";
static const char *kLabelIPAddress = "IP Adresse: ";
static const char *kLabelPrimaryDNS = "Primärer DNS: ";
static const char *kLabelSecondaryDNS = "Sekundärer DNS: ";
static const char *kLabelOptional = "(Optional)";
static const char *kLabelExtendedOptions = "Erweiterte Optionen:";
static const char *kLabelEnabled = "TCP/IP-Protokoll Verwenden";
#else
static const char *kLabelIPCP = "TCP/IP";
static const char *kLabelIPAddress = "IP Address: ";
static const char *kLabelPrimaryDNS = "Primary DNS: ";
static const char *kLabelSecondaryDNS = "Secondary DNS: ";
static const char *kLabelOptional = "(Optional)";
static const char *kLabelExtendedOptions = "Extended Options:";
static const char *kLabelEnabled = "Enable TCP/IP Protocol";
#endif
// add-on descriptions
static const char *kKernelModuleName = "ipcp";
IPCPAddon::IPCPAddon(BMessage *addons)
: DialUpAddon(addons),
fSettings(NULL),
fProfile(NULL)
{
}
IPCPAddon::~IPCPAddon()
{
}
bool
IPCPAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
{
fIsNew = isNew;
fIsEnabled = false;
fIPAddress = fPrimaryDNS = fSecondaryDNS = "";
fSettings = settings;
fProfile = profile;
if(fIPCPView)
fIPCPView->Reload();
// reset all views (empty settings)
if(!settings || !profile || isNew)
return true;
BMessage protocol;
// settings
int32 protocolIndex = FindIPCPProtocol(*fSettings, &protocol);
if(protocolIndex < 0)
return true;
protocol.AddBool(MDSU_VALID, true);
fSettings->ReplaceMessage(MDSU_PARAMETERS, protocolIndex, &protocol);
// profile
protocolIndex = FindIPCPProtocol(*fProfile, &protocol);
if(protocolIndex < 0)
return true;
fIsEnabled = true;
// the "Local" side parameter
BMessage local;
int32 localSideIndex = 0;
if(!FindMessageParameter(IPCP_LOCAL_SIDE_KEY, protocol, &local, &localSideIndex))
local.MakeEmpty();
// just fall through and pretend we have an empty "Local" side parameter
// now load the supported parameters (the client-relevant subset)
BString name;
BMessage parameter;
int32 index = 0;
if(!FindMessageParameter(IPCP_IP_ADDRESS_KEY, local, &parameter, &index)
|| parameter.FindString(MDSU_VALUES, &fIPAddress) != B_OK)
fIPAddress = "";
else {
if(fIPAddress == "auto")
fIPAddress = "";
parameter.AddBool(MDSU_VALID, true);
local.ReplaceMessage(MDSU_PARAMETERS, index, &parameter);
}
index = 0;
if(!FindMessageParameter(IPCP_PRIMARY_DNS_KEY, local, &parameter, &index)
|| parameter.FindString(MDSU_VALUES, &fPrimaryDNS) != B_OK)
fPrimaryDNS = "";
else {
if(fPrimaryDNS == "auto")
fPrimaryDNS = "";
parameter.AddBool(MDSU_VALID, true);
local.ReplaceMessage(MDSU_PARAMETERS, index, &parameter);
}
index = 0;
if(!FindMessageParameter(IPCP_SECONDARY_DNS_KEY, local, &parameter, &index)
|| parameter.FindString(MDSU_VALUES, &fSecondaryDNS) != B_OK)
fSecondaryDNS = "";
else {
if(fSecondaryDNS == "auto")
fSecondaryDNS = "";
parameter.AddBool(MDSU_VALID, true);
local.ReplaceMessage(MDSU_PARAMETERS, index, &parameter);
}
local.AddBool(MDSU_VALID, true);
protocol.ReplaceMessage(MDSU_PARAMETERS, localSideIndex, &local);
protocol.AddBool(MDSU_VALID, true);
fProfile->ReplaceMessage(MDSU_PARAMETERS, protocolIndex, &protocol);
if(fIPCPView)
fIPCPView->Reload();
return true;
}
void
IPCPAddon::IsModified(bool *settings, bool *profile) const
{
if(!fSettings) {
*settings = *profile = false;
return;
}
*settings = fIsEnabled != fIPCPView->IsEnabled();
*profile = (*settings || fIPAddress != fIPCPView->IPAddress()
|| fPrimaryDNS != fIPCPView->PrimaryDNS()
|| fSecondaryDNS != fIPCPView->SecondaryDNS());
}
bool
IPCPAddon::SaveSettings(BMessage *settings, BMessage *profile, bool saveTemporary)
{
if(!fSettings || !settings)
return false;
if(!fIPCPView->IsEnabled())
return true;
BMessage protocol, local;
protocol.AddString(MDSU_NAME, PPP_PROTOCOL_KEY);
protocol.AddString(MDSU_VALUES, kKernelModuleName);
settings->AddMessage(MDSU_PARAMETERS, &protocol);
// the settings contain a simple "protocol ipcp" string
// now create the profile with all subparameters
local.AddString(MDSU_NAME, IPCP_LOCAL_SIDE_KEY);
bool needsLocal = false;
if(fIPCPView->IPAddress() && strlen(fIPCPView->IPAddress()) > 0) {
// save IP address, too
needsLocal = true;
BMessage ip;
ip.AddString(MDSU_NAME, IPCP_IP_ADDRESS_KEY);
ip.AddString(MDSU_VALUES, fIPCPView->IPAddress());
local.AddMessage(MDSU_PARAMETERS, &ip);
}
if(fIPCPView->PrimaryDNS() && strlen(fIPCPView->PrimaryDNS()) > 0) {
// save service name, too
needsLocal = true;
BMessage dns;
dns.AddString(MDSU_NAME, IPCP_PRIMARY_DNS_KEY);
dns.AddString(MDSU_VALUES, fIPCPView->PrimaryDNS());
local.AddMessage(MDSU_PARAMETERS, &dns);
}
if(fIPCPView->SecondaryDNS() && strlen(fIPCPView->SecondaryDNS()) > 0) {
// save service name, too
needsLocal = true;
BMessage dns;
dns.AddString(MDSU_NAME, IPCP_SECONDARY_DNS_KEY);
dns.AddString(MDSU_VALUES, fIPCPView->SecondaryDNS());
local.AddMessage(MDSU_PARAMETERS, &dns);
}
if(needsLocal)
protocol.AddMessage(MDSU_PARAMETERS, &local);
profile->AddMessage(MDSU_PARAMETERS, &protocol);
return true;
}
bool
IPCPAddon::GetPreferredSize(float *width, float *height) const
{
BRect rect;
if(Addons()->FindRect(DUN_TAB_VIEW_RECT, &rect) != B_OK)
rect.Set(0, 0, 200, 300);
// set default values
if(width)
*width = rect.Width();
if(height)
*height = rect.Height();
return true;
}
BView*
IPCPAddon::CreateView(BPoint leftTop)
{
if(!fIPCPView) {
BRect rect;
Addons()->FindRect(DUN_TAB_VIEW_RECT, &rect);
fIPCPView = new IPCPView(this, rect);
fIPCPView->Reload();
}
fIPCPView->MoveTo(leftTop);
return fIPCPView;
}
int32
IPCPAddon::FindIPCPProtocol(const BMessage& message, BMessage *protocol) const
{
if(!protocol)
return -1;
BString name;
for(int32 index = 0; FindMessageParameter(PPP_PROTOCOL_KEY, message, protocol,
&index); index++)
if(protocol->FindString(MDSU_VALUES, &name) == B_OK
&& name == kKernelModuleName)
return index;
return -1;
}
IPCPView::IPCPView(IPCPAddon *addon, BRect frame)
: BView(frame, kLabelIPCP, B_FOLLOW_NONE, 0),
fAddon(addon)
{
BRect rect = Bounds();
rect.InsetBy(10, 10);
rect.bottom = rect.top + 20;
BRect optionalRect(rect);
rect.right -= 75;
fIPAddress = new BTextControl(rect, "ip", kLabelIPAddress, NULL, NULL);
optionalRect.left = rect.right + 5;
optionalRect.bottom = optionalRect.top + 15;
AddChild(new BStringView(optionalRect, "optional_1", kLabelOptional));
rect.top = rect.bottom + 5;
rect.bottom = rect.top + 20;
fPrimaryDNS = new BTextControl(rect, "primaryDNS", kLabelPrimaryDNS, NULL, NULL);
optionalRect.top = rect.top;
optionalRect.bottom = optionalRect.top + 15;
AddChild(new BStringView(optionalRect, "optional_2", kLabelOptional));
rect.top = rect.bottom + 5;
rect.bottom = rect.top + 20;
fSecondaryDNS = new BTextControl(rect, "secondaryDNS", kLabelSecondaryDNS, NULL,
NULL);
optionalRect.top = rect.top;
optionalRect.bottom = optionalRect.top + 15;
AddChild(new BStringView(optionalRect, "optional_3", kLabelOptional));
rect.top = rect.bottom + 50;
rect.bottom = rect.top + 10;
AddChild(new BStringView(rect, "expert", kLabelExtendedOptions));
rect.top = rect.bottom + 5;
rect.bottom = rect.top + 15;
fIsEnabled = new BCheckBox(rect, "isEnabled", kLabelEnabled,
new BMessage(kMsgUpdateControls));
// set divider of text controls
float controlWidth = max(max(StringWidth(fIPAddress->Label()),
StringWidth(fPrimaryDNS->Label())), StringWidth(fSecondaryDNS->Label()));
fIPAddress->SetDivider(controlWidth + 5);
fPrimaryDNS->SetDivider(controlWidth + 5);
fSecondaryDNS->SetDivider(controlWidth + 5);
AddChild(fIsEnabled);
AddChild(fIPAddress);
AddChild(fPrimaryDNS);
AddChild(fSecondaryDNS);
}
void
IPCPView::Reload()
{
fIsEnabled->SetValue(Addon()->IsEnabled() || Addon()->IsNew());
// enable TCP/IP by default
fIPAddress->SetText(Addon()->IPAddress());
fPrimaryDNS->SetText(Addon()->PrimaryDNS());
fSecondaryDNS->SetText(Addon()->SecondaryDNS());
UpdateControls();
}
void
IPCPView::AttachedToWindow()
{
SetViewColor(Parent()->ViewColor());
fIsEnabled->SetTarget(this);
}
void
IPCPView::MessageReceived(BMessage *message)
{
switch(message->what) {
case kMsgUpdateControls:
UpdateControls();
break;
default:
BView::MessageReceived(message);
}
}
void
IPCPView::UpdateControls()
{
fIPAddress->SetEnabled(IsEnabled());
fPrimaryDNS->SetEnabled(IsEnabled());
fSecondaryDNS->SetEnabled(IsEnabled());
}
@@ -0,0 +1,115 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2003-2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
//-----------------------------------------------------------------------
// IPCPAddon saves the loaded settings.
// IPCPView saves the current settings.
//-----------------------------------------------------------------------
#ifndef _IPCP_ADDON__H
#define _IPCP_ADDON__H
#include <DialUpAddon.h>
#include <CheckBox.h>
#include <String.h>
#include <TextControl.h>
class IPCPView;
class IPCPAddon : public DialUpAddon {
public:
IPCPAddon(BMessage *addons);
virtual ~IPCPAddon();
bool IsNew() const
{ return fIsNew; }
bool IsEnabled() const
{ return fIsEnabled; }
const char *IPAddress() const
{ return fIPAddress.String(); }
const char *PrimaryDNS() const
{ return fPrimaryDNS.String(); }
const char *SecondaryDNS() const
{ return fSecondaryDNS.String(); }
BMessage *Settings() const
{ return fSettings; }
BMessage *Profile() const
{ return fProfile; }
virtual int32 Position() const
{ return 10; }
virtual bool LoadSettings(BMessage *settings, BMessage *profile, bool isNew);
virtual void IsModified(bool *settings, bool *profile) const;
virtual bool SaveSettings(BMessage *settings, BMessage *profile,
bool saveTemporary);
virtual bool GetPreferredSize(float *width, float *height) const;
virtual BView *CreateView(BPoint leftTop);
private:
int32 FindIPCPProtocol(const BMessage& message, BMessage *protocol) const;
private:
bool fIsNew, fIsEnabled;
BString fIPAddress, fPrimaryDNS, fSecondaryDNS;
BMessage *fSettings, *fProfile;
// saves last settings state
IPCPView *fIPCPView;
};
class IPCPView : public BView {
public:
IPCPView(IPCPAddon *addon, BRect frame);
IPCPAddon *Addon() const
{ return fAddon; }
void Reload();
bool IsEnabled() const
{ return fIsEnabled->Value(); }
const char *IPAddress() const
{ return fIPAddress->Text(); }
const char *PrimaryDNS() const
{ return fPrimaryDNS->Text(); }
const char *SecondaryDNS() const
{ return fSecondaryDNS->Text(); }
virtual void AttachedToWindow();
virtual void MessageReceived(BMessage *message);
private:
void UpdateControls();
private:
IPCPAddon *fAddon;
BCheckBox *fIsEnabled;
BButton *fCancelButton, *fOKButton;
BTextControl *fIPAddress, *fPrimaryDNS, *fSecondaryDNS;
};
#endif
@@ -0,0 +1,104 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
#include "InterfaceUtils.h"
#include "DialUpAddon.h"
#include <ListView.h>
#include <Menu.h>
#include <MenuItem.h>
#include <Screen.h>
#include <String.h>
#include <ListItem.h> // Contains StringItem class declaration
#include <Window.h>
BPoint
center_on_screen(BRect rect, BWindow *window)
{
BRect screenFrame = (BScreen(window).Frame());
BPoint point((screenFrame.Width() - rect.Width()) / 2.0,
(screenFrame.Height() - rect.Height()) / 2.0);
if(!screenFrame.Contains(point))
point.Set(0, 0);
return point;
}
int32
FindNextMenuInsertionIndex(BMenu *menu, const char *name, int32 index)
{
BMenuItem *item;
for(; index < menu->CountItems(); index++) {
item = menu->ItemAt(index);
if(item && strcasecmp(name, item->Label()) <= 0)
return index;
}
return index;
}
int32
FindNextListInsertionIndex(BListView *list, const char *name)
{
int32 index = 0;
BStringItem *item;
for(; index < list->CountItems(); index++) {
item = static_cast<BStringItem*>(list->ItemAt(index));
if(item && strcasecmp(name, item->Text()) <= 0)
return index;
}
return index;
}
void
AddAddonsToMenu(const BMessage *source, BMenu *menu, const char *type, uint32 what)
{
DialUpAddon *addon;
for(int32 index = 0; source->FindPointer(type, index,
reinterpret_cast<void**>(&addon)) == B_OK; index++) {
if(!addon || (!addon->FriendlyName() && !addon->TechnicalName()))
continue;
BMessage *message = new BMessage(what);
message->AddPointer("Addon", addon);
BString name;
if(addon->TechnicalName()) {
name << addon->TechnicalName();
if(addon->FriendlyName())
name << " (";
}
if(addon->FriendlyName()) {
name << addon->FriendlyName();
if(addon->TechnicalName())
name << ")";
}
int32 insertAt = FindNextMenuInsertionIndex(menu, name.String());
menu->AddItem(new BMenuItem(name.String(), message), insertAt);
}
}
@@ -0,0 +1,43 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
#ifndef _INTERFACE_UTILS__H
#define _INTERFACE_UTILS__H
#include <SupportDefs.h>
class DialUpAddon;
class BListView;
class BMenu;
class BString;
class BWindow;
extern BPoint center_on_screen(BRect rect, BWindow *window = NULL);
extern int32 FindNextMenuInsertionIndex(BMenu *menu, const char *name,
int32 index = 0);
extern int32 FindNextListInsertionIndex(BListView *list, const char *name);
extern void AddAddonsToMenu(const BMessage *source, BMenu *menu, const char *type,
uint32 what);
#endif
@@ -0,0 +1,45 @@
SubDir OBOS_TOP src tests kits net preflet DialUpAddOn ;
# set some additional defines
{
local defines ;
if $(LANG_GERMAN) {
defines += LANG_GERMAN ;
}
defines = [ FDefines $(defines) ] ;
SubDirCcFlags $(defines) ;
SubDirC++Flags $(defines) ;
}
UsePrivateHeaders net ;
# For NetworkSetupAddOn.h, to be moved to private once...
UseHeaders [ FDirName $(OBOS_TOP) src tests kits net preflet ] ;
UseHeaders [ FDirName $(OBOS_TOP) src add-ons kernel network ppp shared libppp headers ] ;
UseHeaders [ FDirName $(OBOS_TOP) src add-ons kernel network ppp shared libkernelppp headers ] ;
# additonal headers for built-in add-ons:
UseHeaders [ FDirName $(OBOS_TOP) src add-ons kernel network ppp pppoe ] ; # PPPoE
UseHeaders [ FDirName $(OBOS_TOP) src add-ons kernel network ppp ipcp ] ; # IPCP
AddResources DialUp : DialUpPreflet.rdef ;
Addon DialUp : network_setup :
AddOn.cpp
DialUpView.cpp
# utils
InterfaceUtils.cpp
MessageDriverSettingsUtils.cpp
TextRequestDialog.cpp
# built-in add-ons
ConnectionOptionsAddon.cpp
GeneralAddon.cpp
IPCPAddon.cpp
PPPoEAddon.cpp
;
LinkSharedOSLibs DialUp : libppp.a be ;
@@ -0,0 +1,258 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
#include "MessageDriverSettingsUtils.h"
#include <PPPDefs.h>
#include <settings_tools.h>
#include <File.h>
#include <Message.h>
#include <String.h>
#include <cstdio>
static bool AddParameters(const BMessage& message, driver_settings *to);
bool
FindMessageParameter(const char *name, const BMessage& message, BMessage *save,
int32 *startIndex)
{
// XXX: this should be removed when we can replace BMessage with something better
BString string;
int32 index = startIndex ? *startIndex : 0;
for(; message.FindMessage(MDSU_PARAMETERS, index, save) == B_OK; index++) {
if(save->FindString(MDSU_NAME, &string) == B_OK
&& string.ICompare(name) == 0) {
if(startIndex)
*startIndex = index;
return true;
}
}
return false;
}
static
bool
AddValues(const BMessage& message, driver_parameter *parameter)
{
const char *value;
for(int32 index = 0; message.FindString(MDSU_VALUES, index, &value) == B_OK;
index++)
if(!add_driver_parameter_value(value, parameter))
return false;
return true;
}
inline
bool
AddParameters(const BMessage& message, driver_parameter *to)
{
if(!to)
return false;
return AddParameters(message,
reinterpret_cast<driver_settings*>(&to->parameter_count));
}
static
bool
AddParameters(const BMessage& message, driver_settings *to)
{
const char *name;
BMessage current;
driver_parameter *parameter;
for(int32 index = 0; message.FindMessage(MDSU_PARAMETERS, index,
&current) == B_OK; index++) {
name = current.FindString(MDSU_NAME);
parameter = new_driver_parameter(name);
if(!AddValues(current, parameter))
return false;
AddParameters(current, parameter);
add_driver_parameter(parameter, to);
}
return true;
}
driver_settings*
MessageToDriverSettings(const BMessage& message)
{
driver_settings *settings = new_driver_settings();
if(!AddParameters(message, settings)) {
free_driver_settings(settings);
return NULL;
}
return settings;
}
static
bool
AddParameter(const driver_parameter *parameter, BMessage *message)
{
if(!parameter || !message)
return false;
if(parameter->name)
message->AddString(MDSU_NAME, parameter->name);
else
return false;
for(int32 index = 0; index < parameter->value_count; index++)
if(parameter->values[index])
message->AddString(MDSU_VALUES, parameter->values[index]);
for(int32 index = 0; index < parameter->parameter_count; index++) {
BMessage parameterMessage;
AddParameter(&parameter->parameters[index], &parameterMessage);
message->AddMessage(MDSU_PARAMETERS, &parameterMessage);
}
return true;
}
bool
ReadMessageDriverSettings(const char *name, BMessage *message)
{
if(!name || !message)
return false;
void *handle = load_driver_settings(name);
if(!handle)
return false;
const driver_settings *settings = get_driver_settings(handle);
if(!settings) {
unload_driver_settings(handle);
return false;
}
for(int32 index = 0; index < settings->parameter_count; index++) {
BMessage parameter;
AddParameter(&settings->parameters[index], &parameter);
message->AddMessage(MDSU_PARAMETERS, &parameter);
}
unload_driver_settings(handle);
return true;
}
static
void
EscapeWord(BString& word)
{
word.ReplaceAll("\\", "\\\\");
word.ReplaceAll("#", "\\#");
word.ReplaceAll("\"", "\\\"");
word.ReplaceAll("\'", "\\\'");
}
static
bool
WriteParameter(BFile& file, const BMessage& parameter, int32 level)
{
const char *name;
if(parameter.FindString(MDSU_NAME, &name) != B_OK || !name)
return false;
BString line, word(name);
EscapeWord(word);
bool needsEscaping = word.FindFirst(' ') >= 0;
line.SetTo('\t', level);
if(needsEscaping)
line << '\"';
line << word;
if(needsEscaping)
line << '\"';
for(int32 index = 0; parameter.FindString(MDSU_VALUES, index, &name) == B_OK;
index++)
if(name) {
line << ' ';
word = name;
EscapeWord(word);
needsEscaping = word.FindFirst(' ') >= 0;
if(needsEscaping)
line << '\"';
line << word;
if(needsEscaping)
line << '\"';
}
type_code type;
int32 parameterCount;
parameter.GetInfo(MDSU_PARAMETERS, &type, &parameterCount);
if(parameterCount > 0)
line << " {";
line << '\n';
file.Write(line.String(), line.Length());
if(parameterCount > 0) {
BMessage subParameter;
for(int32 index = 0; parameter.FindMessage(MDSU_PARAMETERS, index,
&subParameter) == B_OK; index++)
WriteParameter(file, subParameter, level + 1);
line.SetTo('\t', level);
line << "}\n";
file.Write(line.String(), line.Length());
}
return true;
}
bool
WriteMessageDriverSettings(BFile& file, const BMessage& message)
{
if(file.InitCheck() != B_OK || !file.IsWritable())
return false;
file.SetSize(0);
file.Seek(0, SEEK_SET);
BMessage parameter;
for(int32 index = 0; message.FindMessage(MDSU_PARAMETERS, index, &parameter) == B_OK;
index++) {
if(index > 0)
file.Write("\n", 1);
WriteParameter(file, parameter, 0);
}
return true;
}
@@ -0,0 +1,47 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
#ifndef _MESSAGE_DRIVER_SETTINGS_UTILS__H
#define _MESSAGE_DRIVER_SETTINGS_UTILS__H
#include <SupportDefs.h>
struct driver_settings;
class BMessage;
class BFile;
#define MDSU_NAME "Name"
#define MDSU_VALUES "Values"
#define MDSU_PARAMETERS "Parameters"
#define MDSU_VALID "Valid"
extern bool FindMessageParameter(const char *name, const BMessage& message,
BMessage *save, int32 *startIndex = NULL);
extern driver_settings *MessageToDriverSettings(const BMessage& message);
extern bool ReadMessageDriverSettings(const char *name, BMessage *message);
extern bool WriteMessageDriverSettings(BFile& file, const BMessage& message);
#endif
@@ -0,0 +1,420 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2003-2004 Waldemar Kornewald, [email protected]
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
//-----------------------------------------------------------------------
// PPPoEAddon saves the loaded settings.
// PPPoEView saves the current settings.
//-----------------------------------------------------------------------
#include "PPPoEAddon.h"
#include "InterfaceUtils.h"
#include "MessageDriverSettingsUtils.h"
#include "TextRequestDialog.h"
#include <stl_algobase.h>
// for max()
#include <Box.h>
#include <MenuField.h>
#include <MenuItem.h>
#include <PopUpMenu.h>
#include <StringView.h>
#include <PPPManager.h>
#include <PPPoE.h>
// from PPPoE addon
// GUI constants
static const uint32 kDefaultButtonWidth = 80;
// message constants
static const uint32 kMsgSelectInterface = 'SELI';
static const uint32 kMsgSelectOther = 'SELO';
static const uint32 kMsgFinishSelectOther = 'FISO';
static const uint32 kMsgShowServiceWindow = 'SHSW';
static const uint32 kMsgChangeService = 'CHGS';
static const uint32 kMsgResetService = 'RESS';
// labels
#ifdef LANG_GERMAN
static const char *kLabelInterfaceName = "Netzwerk-Adapter: ";
static const char *kLabelOptional = "(Optional)";
static const char *kLabelOtherInterface = "Anderer:";
static const char *kLabelSelectInterface = "Adapter Auswählen...";
static const char *kLabelServiceName = "Service: ";
#else
static const char *kLabelInterfaceName = "Network Interface: ";
static const char *kLabelOptional = "(Optional)";
static const char *kLabelOtherInterface = "Other:";
static const char *kLabelSelectInterface = "Select Interface...";
static const char *kLabelServiceName = "Service: ";
#endif
// requests
#ifdef LANG_GERMAN
static const char *kRequestInterfaceName = "Name Des Adapters: ";
#else
static const char *kRequestInterfaceName = "Network Interface Name: ";
#endif
// add-on descriptions
#ifdef LANG_GERMAN
static const char *kFriendlyName = "Breitband: DSL, Kabel, etc.";
#else
static const char *kFriendlyName = "Broadband: DSL, Cable, etc.";
#endif
static const char *kTechnicalName = "PPPoE";
static const char *kKernelModuleName = "pppoe";
PPPoEAddon::PPPoEAddon(BMessage *addons)
: DialUpAddon(addons),
fSettings(NULL),
fProfile(NULL),
fPPPoEView(NULL)
{
fHeight = 20 // interface name control
+ 20 // service control
+ 5 + 2; // space between controls and bottom
}
PPPoEAddon::~PPPoEAddon()
{
delete fPPPoEView;
// this may have been set to NULL from the view's destructor!
}
const char*
PPPoEAddon::FriendlyName() const
{
return kFriendlyName;
}
const char*
PPPoEAddon::TechnicalName() const
{
return kTechnicalName;
}
const char*
PPPoEAddon::KernelModuleName() const
{
return kKernelModuleName;
}
bool
PPPoEAddon::LoadSettings(BMessage *settings, BMessage *profile, bool isNew)
{
fIsNew = isNew;
fInterfaceName = fServiceName = "";
fSettings = settings;
fProfile = profile;
if(fPPPoEView)
fPPPoEView->Reload();
if(!settings || !profile || isNew)
return true;
BMessage device;
int32 deviceIndex = 0;
if(!FindMessageParameter(PPP_DEVICE_KEY, *fSettings, &device, &deviceIndex))
return false;
// error: no device
BString name;
if(device.FindString(MDSU_VALUES, &name) != B_OK || name != kKernelModuleName)
return false;
// error: no device
BMessage parameter;
int32 index = 0;
if(!FindMessageParameter(PPPoE_INTERFACE_KEY, device, &parameter, &index)
|| parameter.FindString(MDSU_VALUES, &fInterfaceName) != B_OK)
return false;
// error: no interface
else {
parameter.AddBool(MDSU_VALID, true);
device.ReplaceMessage(MDSU_PARAMETERS, index, &parameter);
}
index = 0;
if(!FindMessageParameter(PPPoE_SERVICE_NAME_KEY, device, &parameter, &index)
|| parameter.FindString(MDSU_VALUES, &fServiceName) != B_OK)
fServiceName = "";
else {
parameter.AddBool(MDSU_VALID, true);
device.ReplaceMessage(MDSU_PARAMETERS, index, &parameter);
}
device.AddBool(MDSU_VALID, true);
fSettings->ReplaceMessage(MDSU_PARAMETERS, deviceIndex, &device);
if(fPPPoEView)
fPPPoEView->Reload();
return true;
}
void
PPPoEAddon::IsModified(bool *settings, bool *profile) const
{
*profile = false;
if(!fSettings) {
*settings = false;
return;
}
*settings = (fInterfaceName != fPPPoEView->InterfaceName()
|| fServiceName != fPPPoEView->ServiceName());
}
bool
PPPoEAddon::SaveSettings(BMessage *settings, BMessage *profile, bool saveTemporary)
{
if(!fSettings || !settings || !fPPPoEView->InterfaceName()
|| strlen(fPPPoEView->InterfaceName()) == 0)
return false;
// TODO: tell user that an interface is needed (if we fail because of this)
BMessage device, interface;
device.AddString(MDSU_NAME, PPP_DEVICE_KEY);
device.AddString(MDSU_VALUES, kKernelModuleName);
interface.AddString(MDSU_NAME, PPPoE_INTERFACE_KEY);
interface.AddString(MDSU_VALUES, fPPPoEView->InterfaceName());
device.AddMessage(MDSU_PARAMETERS, &interface);
if(fPPPoEView->ServiceName() && strlen(fPPPoEView->ServiceName()) > 0) {
// save service name, too
BMessage service;
service.AddString(MDSU_NAME, PPPoE_SERVICE_NAME_KEY);
service.AddString(MDSU_VALUES, fPPPoEView->ServiceName());
device.AddMessage(MDSU_PARAMETERS, &service);
}
settings->AddMessage(MDSU_PARAMETERS, &device);
return true;
}
bool
PPPoEAddon::GetPreferredSize(float *width, float *height) const
{
float viewWidth;
if(Addons()->FindFloat(DUN_DEVICE_VIEW_WIDTH, &viewWidth) != B_OK)
viewWidth = 270;
// default value
if(width)
*width = viewWidth;
if(height)
*height = fHeight;
return true;
}
BView*
PPPoEAddon::CreateView(BPoint leftTop)
{
if(!fPPPoEView) {
float width;
if(!Addons()->FindFloat(DUN_DEVICE_VIEW_WIDTH, &width))
width = 270;
// default value
BRect rect(0, 0, width, fHeight);
fPPPoEView = new PPPoEView(this, rect);
fPPPoEView->Reload();
}
fPPPoEView->MoveTo(leftTop);
return fPPPoEView;
}
PPPoEView::PPPoEView(PPPoEAddon *addon, BRect frame)
: BView(frame, "PPPoEView", B_FOLLOW_NONE, 0),
fAddon(addon)
{
BRect rect = Bounds();
rect.InsetBy(5, 0);
rect.bottom = 20;
fInterface = new BMenuField(rect, "interface", kLabelInterfaceName,
new BPopUpMenu(kLabelSelectInterface));
fInterface->SetDivider(StringWidth(fInterface->Label()) + 5);
fInterface->Menu()->AddSeparatorItem();
fOtherInterface = new BMenuItem(kLabelOtherInterface,
new BMessage(kMsgSelectOther));
fInterface->Menu()->AddItem(fOtherInterface);
rect.top = rect.bottom + 5;
rect.bottom = rect.top + 20;
rect.right -= 75;
fServiceName = new BTextControl(rect, "service", kLabelServiceName, NULL, NULL);
fServiceName->SetDivider(StringWidth(fServiceName->Label()) + 5);
rect.left = rect.right + 5;
rect.right += 75;
rect.bottom = rect.top + 15;
AddChild(new BStringView(rect, "optional", kLabelOptional));
AddChild(fInterface);
AddChild(fServiceName);
}
PPPoEView::~PPPoEView()
{
Addon()->UnregisterView();
}
void
PPPoEView::Reload()
{
ReloadInterfaces();
fServiceName->SetText(Addon()->ServiceName());
}
void
PPPoEView::AttachedToWindow()
{
SetViewColor(Parent()->ViewColor());
fInterface->Menu()->SetTargetForItems(this);
fServiceName->SetTarget(this);
}
void
PPPoEView::MessageReceived(BMessage *message)
{
switch(message->what) {
case kMsgSelectInterface: {
BMenuItem *item = fInterface->Menu()->FindMarked();
if(item)
fInterfaceName = item->Label();
} break;
case kMsgSelectOther:
(new TextRequestDialog("InterfaceName", NULL, kRequestInterfaceName,
fInterfaceName.String()))->Go(new BInvoker(
new BMessage(kMsgFinishSelectOther), this));
break;
case kMsgFinishSelectOther: {
int32 which;
message->FindInt32("which", &which);
const char *name = message->FindString("text");
BMenu *menu = fInterface->Menu();
BMenuItem *item;
if(which != 1 || !name || strlen(name) == 0) {
item = menu->FindItem(fInterfaceName.String());
if(item && menu->IndexOf(item) <= menu->CountItems() - 2)
item->SetMarked(true);
else
fOtherInterface->SetMarked(true);
return;
}
fInterfaceName = name;
item = menu->FindItem(fInterfaceName.String());
if(item && menu->IndexOf(item) <= menu->CountItems() - 2) {
item->SetMarked(true);
return;
}
BString label(kLabelOtherInterface);
label << " " << name;
fOtherInterface->SetLabel(label.String());
fOtherInterface->SetMarked(true);
// XXX: this is needed to tell the owning menu to update its label
} break;
default:
BView::MessageReceived(message);
}
}
void
PPPoEView::ReloadInterfaces()
{
// delete all items and request a new bunch from the pppoe kernel module
BMenu *menu = fInterface->Menu();
while(menu->CountItems() > 2)
delete menu->RemoveItem((int32) 0);
fOtherInterface->SetLabel(kLabelOtherInterface);
PPPManager manager;
char *interfaces = new char[8192];
// reserve enough space for approximately 512 entries
int32 count = manager.ControlModule("pppoe", PPPoE_GET_INTERFACES, interfaces,
8192);
BMenuItem *item;
char *name = interfaces;
int32 insertAt;
for(int32 index = 0; index < count; index++) {
item = new BMenuItem(name, new BMessage(kMsgSelectInterface));
insertAt = FindNextMenuInsertionIndex(menu, name);
if(insertAt > menu->CountItems() - 2)
insertAt = menu->CountItems() - 2;
item->SetTarget(this);
menu->AddItem(item, insertAt);
name += strlen(name) + 1;
}
// set interface or some default value if nothing was found
if(Addon()->InterfaceName() && strlen(Addon()->InterfaceName()) > 0)
fInterfaceName = Addon()->InterfaceName();
else if(count > 0)
fInterfaceName = interfaces;
else
fInterfaceName = "";
delete interfaces;
item = menu->FindItem(fInterfaceName.String());
if(item && menu->IndexOf(item) <= menu->CountItems() - 2)
item->SetMarked(true);
else if(Addon()->InterfaceName()) {
BString label(kLabelOtherInterface);
label << " " << fInterfaceName;
fOtherInterface->SetLabel(label.String());
fOtherInterface->SetMarked(true);
}
}
@@ -0,0 +1,113 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2003-2004 Waldemar Kornewald, Waldemar.Kornewald@web.de
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
//-----------------------------------------------------------------------
// PPPoEAddon saves the loaded settings.
// PPPoEView saves the current settings.
//-----------------------------------------------------------------------
#ifndef _PPPoE_ADDON__H
#define _PPPoE_ADDON__H
#include <DialUpAddon.h>
#include <String.h>
#include <TextControl.h>
class PPPoEView;
class PPPoEAddon : public DialUpAddon {
public:
PPPoEAddon(BMessage *addons);
virtual ~PPPoEAddon();
bool IsNew() const
{ return fIsNew; }
const char *InterfaceName() const
{ return fInterfaceName.String(); }
const char *ServiceName() const
{ return fServiceName.String(); }
BMessage *Settings() const
{ return fSettings; }
BMessage *Profile() const
{ return fProfile; }
virtual const char *FriendlyName() const;
virtual const char *TechnicalName() const;
virtual const char *KernelModuleName() const;
virtual bool LoadSettings(BMessage *settings, BMessage *profile, bool isNew);
virtual void IsModified(bool *settings, bool *profile) const;
virtual bool SaveSettings(BMessage *settings, BMessage *profile,
bool saveTemporary);
virtual bool GetPreferredSize(float *width, float *height) const;
virtual BView *CreateView(BPoint leftTop);
void UnregisterView()
{ fPPPoEView = NULL; }
private:
bool fIsNew;
BString fInterfaceName, fServiceName;
BMessage *fSettings, *fProfile;
// saves last settings state
PPPoEView *fPPPoEView;
float fHeight;
// height of PPPoEView
};
class PPPoEView : public BView {
public:
PPPoEView(PPPoEAddon *addon, BRect frame);
virtual ~PPPoEView();
PPPoEAddon *Addon() const
{ return fAddon; }
void Reload();
const char *InterfaceName() const
{ return fInterfaceName.String(); }
const char *ServiceName() const
{ return fServiceName->Text(); }
virtual void AttachedToWindow();
virtual void MessageReceived(BMessage *message);
private:
void ReloadInterfaces();
private:
PPPoEAddon *fAddon;
BMenuField *fInterface;
BMenuItem *fOtherInterface;
BString fInterfaceName;
BTextControl *fServiceName;
};
#endif
@@ -0,0 +1,10 @@
Short-term TODOs:
- add "Revert Changes" button
- load add-ons from /boot/home/config/add-ons/DialUpPreflet
- move DEVNOTES into a doxygen file and document the rest of the API
- IPCP: check for incorrect settings (only IP addresses should be entered)
- PPPoE: refresh interfaces list every second or so
- ConnectionOptions: add field for entering number of dial retries and delay between retries
Long-term TODOs:
- (maybe) allow selecting multiple authenticators (in expert-mode)
@@ -0,0 +1,164 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2004 Waldemar Kornewald, Waldemar.Kornewald@web.de
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
#include "TextRequestDialog.h"
#include "InterfaceUtils.h"
#include <Button.h>
#include <TextControl.h>
#include <TextView.h>
// GUI constants
static const uint32 kWindowWidth = 250;
static const uint32 kWindowHeight = 10 + 20 + 10 + 25 + 5;
static const BRect kWindowRect(0, 0, kWindowWidth, kWindowHeight);
static const uint32 kDefaultButtonWidth = 80;
// message constants
static const uint32 kMsgButton = 'MBTN';
static const uint32 kMsgUpdateControls = 'UCTL';
// labels
static const char *kLabelOK = "OK";
static const char *kLabelCancel = "Cancel";
TextRequestDialog::TextRequestDialog(const char *title, const char *information,
const char *request, const char *text)
: BWindow(kWindowRect, title, B_MODAL_WINDOW, B_NOT_RESIZABLE | B_NOT_CLOSABLE, 0),
fInvoker(NULL)
{
BRect rect = Bounds();
BView *backgroundView = new BView(rect, "background", B_FOLLOW_ALL_SIDES, 0);
backgroundView->SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR));
rect.InsetBy(5, 5);
rect.bottom = rect.top;
// init
if(information) {
BRect textRect(rect);
textRect.OffsetTo(0, 0);
fTextView = new BTextView(rect, "TextView", textRect, B_FOLLOW_NONE,
B_WILL_DRAW);
fTextView->SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR));
fTextView->MakeSelectable(false);
fTextView->MakeEditable(false);
fTextView->SetText(information);
float textHeight = fTextView->TextHeight(0, fTextView->CountLines());
backgroundView->ResizeBy(0, textHeight + 5);
ResizeBy(0, textHeight + 5);
fTextView->ResizeBy(0, textHeight - textRect.Height());
rect.bottom += textHeight + 5;
backgroundView->AddChild(fTextView);
} else
fTextView = NULL;
rect.top = rect.bottom + 5;
rect.bottom = rect.top + 20;
fTextControl = new BTextControl(rect, "request", request, text, NULL);
fTextControl->SetModificationMessage(new BMessage(kMsgUpdateControls));
fTextControl->SetDivider(fTextControl->StringWidth(fTextControl->Label()) + 5);
if(text && strlen(text) > 0)
fTextControl->TextView()->SelectAll();
rect.top = rect.bottom + 10;
rect.bottom = rect.top + 25;
rect.left = rect.right - kDefaultButtonWidth;
BMessage message(kMsgButton);
message.AddInt32("which", 1);
fOKButton = new BButton(rect, "okButton", kLabelOK, new BMessage(message));
rect.right = rect.left - 10;
rect.left = rect.right - kDefaultButtonWidth;
message.ReplaceInt32("which", 0);
BButton *cancelButton = new BButton(rect, "cancelButton", kLabelCancel,
new BMessage(message));
backgroundView->AddChild(cancelButton);
backgroundView->AddChild(fOKButton);
backgroundView->AddChild(fTextControl);
AddChild(backgroundView);
fTextControl->MakeFocus(true);
SetDefaultButton(fOKButton);
UpdateControls();
}
TextRequestDialog::~TextRequestDialog()
{
delete fInvoker;
}
void
TextRequestDialog::MessageReceived(BMessage *message)
{
switch(message->what) {
case kMsgButton: {
if(!fInvoker || !fInvoker->Message())
return;
int32 which;
message->FindInt32("which", &which);
BMessage toSend(*fInvoker->Message());
toSend.AddInt32("which", which);
if(which == 1)
toSend.AddString("text", fTextControl->Text());
fInvoker->Invoke(&toSend);
PostMessage(B_QUIT_REQUESTED);
} break;
case kMsgUpdateControls:
UpdateControls();
break;
default:
BWindow::MessageReceived(message);
}
}
bool
TextRequestDialog::QuitRequested()
{
return true;
}
status_t
TextRequestDialog::Go(BInvoker *invoker)
{
fInvoker = invoker;
MoveTo(center_on_screen(Bounds()));
Show();
return B_OK;
}
void
TextRequestDialog::UpdateControls()
{
fOKButton->SetEnabled(fTextControl->TextView()->TextLength() > 0);
}
@@ -0,0 +1,52 @@
/* -----------------------------------------------------------------------
* Copyright (c) 2004 Waldemar Kornewald, Waldemar.Kornewald@web.de
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
* ----------------------------------------------------------------------- */
#ifndef _TEXT_REQUEST_DIALOG__H
#define _TEXT_REQUEST_DIALOG__H
#include <Window.h>
class TextRequestDialog : public BWindow {
public:
TextRequestDialog(const char *title, const char *information,
const char *request, const char *text = NULL);
virtual ~TextRequestDialog();
virtual void MessageReceived(BMessage *message);
virtual bool QuitRequested();
status_t Go(BInvoker *invoker);
private:
void UpdateControls();
private:
BTextView *fTextView;
// displays information text
BButton *fOKButton;
BTextControl *fTextControl;
BInvoker *fInvoker;
};
#endif
@@ -0,0 +1,92 @@
/*
* Copyright (c) 1986, 1993
* The Regents of the University of California. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by the University of
* California, Berkeley and its contributors.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* @(#)if_arp.h 8.1 (Berkeley) 6/10/93
*/
#ifndef NET_IF_ARP_H
#define NET_IF_ARP_H
/*
* Address Resolution Protocol.
*
* See RFC 826 for protocol description. ARP packets are variable
* in size; the arphdr structure defines the fixed-length portion.
* Protocol type values are the same as those for 10 Mb/s Ethernet.
* It is followed by the variable-sized fields ar_sha, arp_spa,
* arp_tha and arp_tpa in that order, according to the lengths
* specified. Field names used correspond to RFC 826.
*/
struct arphdr {
uint16 ar_hrd; /* format of hardware address */
uint16 ar_pro; /* format of protocol address */
uint8 ar_hln; /* length of hardware address */
uint8 ar_pln; /* length of protocol address */
uint16 ar_op; /* one of: */
/*
* The remaining fields are variable in size,
* according to the sizes above.
*/
#ifdef COMMENT_ONLY
uint8 ar_sha[]; /* sender hardware address */
uint8 ar_spa[]; /* sender protocol address */
uint8 ar_tha[]; /* target hardware address */
uint8 ar_tpa[]; /* target protocol address */
#endif
};
#define ARPHRD_ETHER 1 /* ethernet hardware format */
#define ARPHRD_IEEE802 6 /* IEEE 802 hardware format */
#define ARPHRD_FRELAY 15 /* frame relay hardware format */
#define ARPOP_REQUEST 1 /* request to resolve address */
#define ARPOP_REPLY 2 /* response to previous request */
#define ARPOP_REVREQUEST 3 /* request protocol address given hardware */
#define ARPOP_REVREPLY 4 /* response giving protocol address */
#define ARPOP_INVREQUEST 8 /* request to identify peer */
#define ARPOP_INVREPLY 9 /* response identifying peer */
/*
* ARP ioctl request
*/
struct arpreq {
struct sockaddr arp_pa; /* protocol address */
struct sockaddr arp_ha; /* hardware address */
int arp_flags; /* flags */
};
/* arp_flags and at_flags field values */
#define ATF_INUSE 0x01 /* entry in use */
#define ATF_COM 0x02 /* completed entry (enaddr valid) */
#define ATF_PERM 0x04 /* permanent entry */
#define ATF_PUBL 0x08 /* publish entry (respond for other host) */
#define ATF_USETRAILERS 0x10 /* has requested trailers */
#endif /* NET_IF_ARP_H */
@@ -0,0 +1,198 @@
/*
* Copyright (c) 1982, 1986, 1993
* The Regents of the University of California. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by the University of
* California, Berkeley and its contributors.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* @(#)if_ether.h 8.1 (Berkeley) 6/10/93
*/
#ifndef NETINET_IF_ETHER_H
#define NETINET_IF_ETHER_H
#include "net/if_arp.h"
/*
* Ethernet address - 6 octets
* this is only used by the ethers(3) functions.
*/
struct ether_addr {
uint8 ether_addr_octet[6];
};
/*
* Some Ethernet constants.
*/
#define ETHER_ADDR_LEN 6 /* Ethernet address length */
#define ETHER_TYPE_LEN 2 /* Ethernet type field length */
#define ETHER_CRC_LEN 4 /* Ethernet CRC lenght */
#define ETHER_HDR_LEN ((ETHER_ADDR_LEN * 2) + ETHER_TYPE_LEN)
#define ETHER_MIN_LEN 64 /* Minimum frame length, CRC included */
#define ETHER_MAX_LEN 1518 /* Maximum frame length, CRC included */
struct ether_header {
uint8 ether_dhost[ETHER_ADDR_LEN];
uint8 ether_shost[ETHER_ADDR_LEN];
uint16 ether_type;
};
#define ETHERTYPE_PUP 0x0200 /* PUP protocol */
#define ETHERTYPE_IP 0x0800 /* IP protocol */
#define ETHERTYPE_ARP 0x0806 /* address resolution protocol */
#define ETHERTYPE_REVARP 0x8035 /* reverse addr resolution protocol */
#define ETHERTYPE_8021Q 0x8100 /* IEEE 802.1Q VLAN tagging */
#define ETHERTYPE_IPV6 0x86DD /* IPv6 protocol */
#define ETHERTYPE_PPPOEDISC 0x8863 /* PPP Over Ethernet Discovery Stage */
#define ETHERTYPE_PPPOE 0x8864 /* PPP Over Ethernet Session Stage */
#define ETHERTYPE_LOOPBACK 0x9000 /* used to test interfaces */
#define ETHER_IS_MULTICAST(addr) (*(addr) & 0x01) /* is address mcast/bcast? */
#define ETHERMTU (ETHER_MAX_LEN - ETHER_HDR_LEN - ETHER_CRC_LEN)
#define ETHERMIN (ETHER_MIN_LEN - ETHER_HDR_LEN - ETHER_CRC_LEN)
//#ifdef _NETWORK_STACK
/*
* Macro to map an IP multicast address to an Ethernet multicast address.
* The high-order 25 bits of the Ethernet address are statically assigned,
* and the low-order 23 bits are taken from the low end of the IP address.
*/
#define ETHER_MAP_IP_MULTICAST(ipaddr, enaddr) \
/* struct in_addr *ipaddr; */ \
/* u_int8_t enaddr[ETHER_ADDR_LEN]; */ \
{ \
(enaddr)[0] = 0x01; \
(enaddr)[1] = 0x00; \
(enaddr)[2] = 0x5e; \
(enaddr)[3] = ((uint8 *)ipaddr)[1] & 0x7f; \
(enaddr)[4] = ((uint8 *)ipaddr)[2]; \
(enaddr)[5] = ((uint8 *)ipaddr)[3]; \
}
/*
* Macro to map an IPv6 multicast address to an Ethernet multicast address.
* The high-order 16 bits of the Ethernet address are statically assigned,
* and the low-order 32 bits are taken from the low end of the IPv6 address.
*/
#define ETHER_MAP_IPV6_MULTICAST(ip6addr, enaddr) \
/* struct in6_addr *ip6addr; */ \
/* u_int8_t enaddr[ETHER_ADDR_LEN]; */ \
{ \
(enaddr)[0] = 0x33; \
(enaddr)[1] = 0x33; \
(enaddr)[2] = ((u_int8_t *)ip6addr)[12]; \
(enaddr)[3] = ((u_int8_t *)ip6addr)[13]; \
(enaddr)[4] = ((u_int8_t *)ip6addr)[14]; \
(enaddr)[5] = ((u_int8_t *)ip6addr)[15]; \
}
//#endif
/*
* Structure shared between the ethernet driver modules and
* the address resolution code. For example, each ec_softc or il_softc
* begins with this structure.
*/
struct arpcom {
struct ifnet ac_if; /* network-visible interface */
uint8 ac_enaddr[ETHER_ADDR_LEN]; /* ethernet hardware address */
struct in_addr ac_ipaddr;
char ac__pad[2]; /* pad for some machines */
// struct ether_multi *ac_multiaddrs; /* list of ether multicast addrs */
int ac_multicnt; /* length of ac_multiaddrs list */
};
struct ether_device {
struct arpcom sc_ac;
struct ether_device *next; /* next ether_device */
};
#define sc_if sc_ac.ac_if
#define sc_addr sc_ac.ac_enaddr
struct ether_arp {
struct arphdr ea_hdr;
u_char arp_sha[6];
u_char arp_spa[4];
u_char arp_tha[6];
u_char arp_tpa[4];
};
#define arp_hrd ea_hdr.ar_hrd
#define arp_pro ea_hdr.ar_pro
#define arp_hln ea_hdr.ar_hln
#define arp_pln ea_hdr.ar_pln
#define arp_op ea_hdr.ar_op
struct llinfo_arp {
struct llinfo_arp *la_next;
struct llinfo_arp *la_prev;
struct rtentry *la_rt;
struct mbuf *la_hold;
int32 la_asked;
};
#define la_timer la_rt->rt_rmx.rmx_expire
struct sockaddr_inarp {
uint8 sin_len;
uint8 sin_family;
uint16 sin_port;
struct in_addr sin_addr;
struct in_addr sin_srcaddr;
uint16 sin_tos;
uint16 sin_other;
};
#define SIN_PROXY 1
/*
* IP and ethernet specific routing flags
*/
#define RTF_USETRAILERS RTF_PROTO1 /* use trailers */
#define RTF_ANNOUNCE RTF_PROTO2 /* announce new arp entry */
#define RTF_PERMANENT_ARP RTF_PROTO3 /* only manual overwrite of entry */
//#ifdef _NETWORK_STACK
int arpresolve(struct arpcom *ac, struct rtentry *rt, struct mbuf *m,
struct sockaddr *dst, uint8 *desten);
//void arpwhohas(struct arpcom *ac, struct in_addr *ia);
//#else
char *ether_ntoa (struct ether_addr *);
struct ether_addr *ether_aton (char *);
int ether_ntohost (char *, struct ether_addr *);
int ether_hostton (char *, struct ether_addr *);
int ether_line(char *line, struct ether_addr *e, char *hostname);
//#endif
#endif /* NETINET_IF_ETHER_H */
Binary file not shown.
@@ -0,0 +1,11 @@
#include <stdlib.h>
#include "NetworkSetupAddOn.h"
NetworkSetupAddOn*
get_nth_addon(image_id image, int index)
{
if (index != 0)
return NULL;
return new NetworkSetupAddOn(image);
}
+1
View File
@@ -0,0 +1 @@
../NetworkSetup
+19 -3
View File
@@ -1,10 +1,26 @@
SubDir HAIKU_TOP src tests kits net preflet ;
SimpleTest NetworkSetup :
SimpleTest Network_Setup :
NetworkSetup.cpp
NetworkSetupWindow.cpp
NetworkSetupProfile.cpp
NetworkSetupAddOn.cpp
BoneyardAddOn.cpp
: be root $(TARGET_LIBSUPC++)
: be root
;
{
# symlink the userland add-ons dir to the dir where the net_stack_tester lives
local dir = [ on Network\_Setup return $(LOCATE) ] ;
MakeLocate <network_setup-add-ons>network_setup : $(HAIKU_ADDON_DIR) ;
MakeLocate <network_setup-add-ons>add-ons : $(dir) ;
RelSymLink <network_setup-add-ons>add-ons : <network_setup-add-ons>network_setup : false ;
# alias for the stack_tester the modules link against
LOCATE on <installed>Network_Setup = $(dir) ;
Depends <installed>Network_Setup : Network_Setup ;
}
# SubInclude HAIKU_TOP src tests kits net preflet StatusAddOn ;
# SubInclude HAIKU_TOP src tests kits net preflet ServicesAddOn ;
# SubInclude HAIKU_TOP src tests kits net preflet DialUpAddOn ;
@@ -0,0 +1,62 @@
#include <stdlib.h>
#include <stdio.h>
#include "NetworkSetupAddOn.h"
class MultipleAddOn : public NetworkSetupAddOn {
public:
MultipleAddOn(image_id addon_image, int index);
~MultipleAddOn();
BView* CreateView(BRect* bounds);
const char* Name();
private:
char* fName;
rgb_color fViewColor;
};
MultipleAddOn::MultipleAddOn(image_id image, int i)
:
NetworkSetupAddOn(image)
{
fName = (char*) malloc(64);
sprintf(fName, "Multi #%d", i);
fViewColor.red = rand() % 256;
fViewColor.blue = rand() % 256;
fViewColor.green = rand() % 256;
fViewColor.alpha = 255;
}
MultipleAddOn::~MultipleAddOn()
{
free(fName);
}
BView*
MultipleAddOn::CreateView(BRect* bounds)
{
BView *v = new BView(*bounds, "a view", B_FOLLOW_ALL, B_WILL_DRAW);
v->SetViewColor(fViewColor);
return v;
}
const char*
MultipleAddOn::Name()
{
return fName;
}
NetworkSetupAddOn*
get_nth_addon(image_id image, int index)
{
if (index < 0 || index > 3)
return NULL;
return new MultipleAddOn(image, index);
}
+1
View File
@@ -0,0 +1 @@
../NetworkSetup
-81
View File
@@ -1,81 +0,0 @@
#include <Application.h>
#include <Window.h>
#include <Alert.h>
#include "NetworkWindow.h"
#define SOFTWARE_EDITOR "obos"
#define SOFTWARE_NAME "Network"
#define SOFTWARE_VERSION_LABEL "0.1.0 alpha"
const char * APPLICATION_SIGNATURE = "application/x-vnd." SOFTWARE_EDITOR "-" SOFTWARE_NAME;
const char * STR_ABOUT_TITLE = "About " SOFTWARE_NAME;
const char * STR_ABOUT_BUTTON = "Big Deal"; // "Hum?"
const char * STR_ABOUT_TEXT = SOFTWARE_NAME " " SOFTWARE_VERSION_LABEL "\n" \
"A little Network setup tool.\n\n" \
"The " SOFTWARE_NAME " Team:\n\n" \
"OpenBeOS Networking Team\n" \
"\n" \
"Thanks to:\n" \
"Be Inc.\n" \
"Internet\n" \
"Life\n";
class Application : public BApplication
{
public:
// Constructors, destructors, operators...
Application();
public:
// Virtual function overrides
void ReadyToRun(void);
// virtual void MessageReceived(BMessage * msg);
virtual void AboutRequested();
};
// --------------------------------------------------------------
int main()
{
// Create an application instance
Application * app;
app = new Application();
app->Run();
delete app;
return 0;
}
// --------------------------------------------------------------
Application::Application()
: BApplication(APPLICATION_SIGNATURE)
{
}
// -------------------------------------------------
void Application::ReadyToRun(void)
{
// Open at least one window!
NetworkWindow *window;
window = new NetworkWindow(SOFTWARE_NAME);
window->Show();
}
// -------------------------------------------------
void Application::AboutRequested(void)
{
BAlert * about_box;
about_box = new BAlert(STR_ABOUT_TITLE, STR_ABOUT_TEXT, STR_ABOUT_BUTTON);
about_box->Go();
}
+6 -44
View File
@@ -5,77 +5,39 @@
#include "NetworkSetupWindow.h"
#define SOFTWARE_EDITOR "Haiku"
#define SOFTWARE_NAME "Network Settings"
#define NAME "NetworkSettings"
#define SOFTWARE_VERSION_LABEL "0.1.0 alpha"
const char * APPLICATION_SIGNATURE = "application/x-vnd." SOFTWARE_EDITOR "-" SOFTWARE_NAME;
const char * STR_ABOUT_TITLE = "About " SOFTWARE_NAME;
const char * STR_ABOUT_BUTTON = "Big Deal"; // "Hum?"
const char * STR_ABOUT_TEXT = SOFTWARE_NAME " " SOFTWARE_VERSION_LABEL "\n" \
"A little Network setup tool.\n\n" \
"The " SOFTWARE_NAME " Team:\n\n" \
"OpenBeOS Networking Team\n" \
"\n" \
"Thanks to:\n" \
"Be Inc.\n" \
"Internet\n" \
"Life\n";
#define APPLICATION_SIGNATURE "application/x-vnd." SOFTWARE_EDITOR "-" NAME
class Application : public BApplication
{
public:
// Constructors, destructors, operators...
Application();
public:
// Virtual function overrides
void ReadyToRun(void);
// virtual void MessageReceived(BMessage * msg);
virtual void AboutRequested();
};
// --------------------------------------------------------------
int main()
{
// Create an application instance
Application * app;
app = new Application();
Application* app = new Application();
app->Run();
delete app;
return 0;
}
// --------------------------------------------------------------
Application::Application()
: BApplication(APPLICATION_SIGNATURE)
{
}
// -------------------------------------------------
void Application::ReadyToRun(void)
void
Application::ReadyToRun(void)
{
// Open at least one window!
NetworkSetupWindow *window;
window = new NetworkSetupWindow(SOFTWARE_NAME);
NetworkSetupWindow* window = new NetworkSetupWindow(SOFTWARE_NAME);
window->Show();
}
// -------------------------------------------------
void Application::AboutRequested(void)
{
BAlert * about_box;
about_box = new BAlert(STR_ABOUT_TITLE, STR_ABOUT_TEXT, STR_ABOUT_BUTTON);
about_box->Go();
}
Binary file not shown.
@@ -5,18 +5,24 @@
#include "NetworkSetupAddOn.h"
NetworkSetupAddOn::NetworkSetupAddOn(image_id image)
: m_is_dirty(false), m_profile(NULL), m_addon_image(image), m_addon_resources(NULL)
:
fIsDirty(false),
fProfile(NULL),
fAddonImage(image),
fAddonResources(NULL)
{
}
NetworkSetupAddOn::~NetworkSetupAddOn()
{
delete m_addon_resources;
delete fAddonResources;
}
BView * NetworkSetupAddOn::CreateView(BRect *bounds)
BView*
NetworkSetupAddOn::CreateView(BRect* bounds)
{
BView *v = new BView(*bounds, "a view", B_FOLLOW_ALL, B_WILL_DRAW);
v->SetViewColor((rand() % 256), (rand() % 256), (rand() % 256));
@@ -24,47 +30,78 @@ BView * NetworkSetupAddOn::CreateView(BRect *bounds)
}
status_t NetworkSetupAddOn::Save()
status_t
NetworkSetupAddOn::Save()
{
return B_OK;
}
status_t NetworkSetupAddOn::Revert()
status_t
NetworkSetupAddOn::Revert()
{
return B_OK;
}
status_t NetworkSetupAddOn::ProfileChanged(NetworkSetupProfile *new_profile)
status_t
NetworkSetupAddOn::ProfileChanged(NetworkSetupProfile* new_profile)
{
m_profile = new_profile;
fProfile = new_profile;
return B_OK;
}
const char * NetworkSetupAddOn::Name()
bool
NetworkSetupAddOn::IsDirty()
{
return fIsDirty;
}
void
NetworkSetupAddOn::SetDirty(bool dirty)
{
fIsDirty = dirty;
}
NetworkSetupProfile*
NetworkSetupAddOn::Profile()
{
return fProfile;
}
image_id
NetworkSetupAddOn::ImageId()
{
return fAddonImage;
}
const char*
NetworkSetupAddOn::Name()
{
return "Dummy NetworkSetupAddon";
}
BResources * NetworkSetupAddOn::Resources()
BResources*
NetworkSetupAddOn::Resources()
{
if (!m_addon_resources) {
if (!fAddonResources) {
image_info info;
if (get_image_info(m_addon_image, &info) != B_OK)
if (get_image_info(fAddonImage, &info) != B_OK)
return NULL;
BResources *resources = new BResources();
BFile addon_file(info.name, O_RDONLY);
if (resources->SetTo(&addon_file) == B_OK)
m_addon_resources = resources;
fAddonResources = resources;
else
delete resources;
};
return m_addon_resources;
}
return fAddonResources;
}
+11 -18
View File
@@ -12,41 +12,34 @@ class NetworkSetupAddOn {
NetworkSetupAddOn(image_id addon_image);
virtual ~NetworkSetupAddOn();
virtual BView * CreateView(BRect *bounds);
virtual BView * CreateView(BRect* bounds);
virtual status_t Save();
virtual status_t Revert();
virtual const char * Name();
// virtual const BBitmap * Icon();
virtual status_t ProfileChanged(NetworkSetupProfile *new_profile);
virtual status_t ProfileChanged(NetworkSetupProfile*
new_profile);
NetworkSetupProfile * Profile();
bool IsDirty();
void SetDirty(bool dirty = true);
image_id ImageId();
BResources * Resources();
BResources* Resources();
private:
bool m_is_dirty;
NetworkSetupProfile * m_profile;
image_id m_addon_image;
BResources * m_addon_resources;
bool fIsDirty;
NetworkSetupProfile* fProfile;
image_id fAddonImage;
BResources* fAddonResources;
};
inline bool NetworkSetupAddOn::IsDirty() { return m_is_dirty; };
inline void NetworkSetupAddOn::SetDirty(bool dirty) { m_is_dirty = dirty; };
inline NetworkSetupProfile * NetworkSetupAddOn::Profile() { return m_profile; };
inline image_id NetworkSetupAddOn::ImageId() { return m_addon_image; };
extern "C" {
#define NETWORK_SETUP_ADDON_INSTANCIATE_FUNC_NAME "get_nth_addon"
typedef NetworkSetupAddOn * (*network_setup_addon_instantiate)(image_id image, int index);
typedef NetworkSetupAddOn* (*network_setup_addon_instantiate)(image_id image,
int index);
extern NetworkSetupAddOn * get_nth_addon(image_id image, int index);
extern NetworkSetupAddOn* get_nth_addon(image_id image, int index);
}
#endif // ifdef NETWORKSETUPADDON_H
@@ -4,22 +4,26 @@
NetworkSetupProfile::NetworkSetupProfile()
:
fRoot(new BEntry()),
fPath(new BPath())
{
root = new BEntry();
path = new BPath();
}
NetworkSetupProfile::NetworkSetupProfile(const char *path)
NetworkSetupProfile::NetworkSetupProfile(const char* path)
{
SetTo(path);
}
NetworkSetupProfile::NetworkSetupProfile(const entry_ref *ref)
NetworkSetupProfile::NetworkSetupProfile(const entry_ref* ref)
{
SetTo(ref);
}
NetworkSetupProfile::NetworkSetupProfile(BEntry *entry)
NetworkSetupProfile::NetworkSetupProfile(BEntry* entry)
{
SetTo(entry);
}
@@ -27,92 +31,100 @@ NetworkSetupProfile::NetworkSetupProfile(BEntry *entry)
NetworkSetupProfile::~NetworkSetupProfile()
{
delete root;
delete fRoot;
}
status_t NetworkSetupProfile::SetTo(const char *path)
status_t
NetworkSetupProfile::SetTo(const char* path)
{
BEntry *entry = new BEntry(path);
SetTo(entry);
SetTo(new BEntry(path));
return B_OK;
}
status_t NetworkSetupProfile::SetTo(const entry_ref *ref)
status_t
NetworkSetupProfile::SetTo(const entry_ref* ref)
{
BEntry *entry = new BEntry(ref);
SetTo(entry);
SetTo(new BEntry(ref));
return B_OK;
}
status_t NetworkSetupProfile::SetTo(BEntry *entry)
status_t
NetworkSetupProfile::SetTo(BEntry *entry)
{
delete root;
delete path;
root = entry;
delete fRoot;
delete fPath;
fRoot = entry;
return B_OK;
}
const char * NetworkSetupProfile::Name()
const char*
NetworkSetupProfile::Name()
{
if (!name) {
root->GetPath(path);
name = path->Leaf();
};
if (!fName) {
fRoot->GetPath(fPath);
fName = fPath->Leaf();
}
return name;
return fName;
}
status_t NetworkSetupProfile::SetName(const char *name)
status_t
NetworkSetupProfile::SetName(const char* name)
{
return B_OK;
}
bool NetworkSetupProfile::Exists()
bool
NetworkSetupProfile::Exists()
{
return root->Exists();
return fRoot->Exists();
}
status_t NetworkSetupProfile::Delete()
status_t
NetworkSetupProfile::Delete()
{
return B_ERROR;
}
bool NetworkSetupProfile::IsDefault()
bool
NetworkSetupProfile::IsDefault()
{
return is_default;
return fIsDefault;
}
bool NetworkSetupProfile::IsCurrent()
bool
NetworkSetupProfile::IsCurrent()
{
return is_current;
return fIsCurrent;
}
status_t NetworkSetupProfile::MakeCurrent()
status_t
NetworkSetupProfile::MakeCurrent()
{
return B_ERROR;
}
// #pragma mark -
NetworkSetupProfile * NetworkSetupProfile::Default()
NetworkSetupProfile*
NetworkSetupProfile::Default()
{
return NULL;
}
NetworkSetupProfile * NetworkSetupProfile::Current()
NetworkSetupProfile*
NetworkSetupProfile::Current()
{
return NULL;
}
@@ -6,19 +6,19 @@
class NetworkSetupProfile {
public:
NetworkSetupProfile();
NetworkSetupProfile(const char *path);
NetworkSetupProfile(const entry_ref *ref);
NetworkSetupProfile(const char* path);
NetworkSetupProfile(const entry_ref* ref);
NetworkSetupProfile(BEntry *entry);
virtual ~NetworkSetupProfile();
status_t SetTo(const char *path);
status_t SetTo(const char* path);
status_t SetTo(const entry_ref *ref);
status_t SetTo(BEntry *entry);
bool Exists();
const char * Name();
const char* Name();
status_t SetName(const char *name);
@@ -28,19 +28,16 @@ virtual ~NetworkSetupProfile();
status_t MakeCurrent();
status_t Delete();
static NetworkSetupProfile * Default();
static NetworkSetupProfile * Current();
static NetworkSetupProfile* Default();
static NetworkSetupProfile* Current();
private:
BEntry * root;
BPath * path;
bool is_default;
bool is_current;
const char * name;
BEntry* fRoot;
BPath* fPath;
bool fIsDefault;
bool fIsCurrent;
const char* fName;
static BDirectory * profiles_root;
static BDirectory* fProfilesRoot;
};
#endif // ifdef NETWORKSETUPPROFILE_H
+63 -139
View File
@@ -1,3 +1,4 @@
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
@@ -8,15 +9,14 @@
#include <StorageKit.h>
#include <SupportKit.h>
#include "BoneyardAddOn.h"
#include "NetworkSetupAddOn.h"
#include "NetworkSetupWindow.h"
// --------------------------------------------------------------
NetworkSetupWindow::NetworkSetupWindow(const char *title)
: BWindow(BRect(100, 100, 600, 600), title, B_TITLED_WINDOW,
B_ASYNCHRONOUS_CONTROLS | B_NOT_ZOOMABLE)
:
BWindow(BRect(100, 100, 600, 600), title, B_TITLED_WINDOW
, B_ASYNCHRONOUS_CONTROLS | B_NOT_ZOOMABLE)
{
BMenu *show_menu;
BMenu *profiles_menu;
@@ -29,9 +29,8 @@ NetworkSetupWindow::NetworkSetupWindow(const char *title)
float size, min_size = 360;
// TODO: cleanup this mess!
show_menu = new BPopUpMenu("<please select me!>");
BuildShowMenu(show_menu, SHOW_MSG);
_BuildShowMenu(show_menu, SHOW_MSG);
#define H_MARGIN 10
#define V_MARGIN 10
@@ -49,14 +48,13 @@ NetworkSetupWindow::NetworkSetupWindow(const char *title)
r.InsetBy(H_MARGIN, V_MARGIN);
// ---- Profiles section
profiles_menu = new BPopUpMenu("<none>");
menu_field = new BMenuField(r, "profiles_menu", PROFILE_LABEL, profiles_menu);
menu_field = new BMenuField(r, "profiles_menu", PROFILE_LABEL,
profiles_menu);
menu_field->SetFont(be_bold_font);
menu_field->SetDivider(be_bold_font->StringWidth(PROFILE_LABEL "#"));
top_box->AddChild(menu_field);
// menu_field->SetViewColor((rand() % 256), (rand() % 256), (rand() % 256));
menu_field->ResizeToPreferred();
menu_field->GetPreferredSize(&w, &h);
@@ -81,7 +79,7 @@ NetworkSetupWindow::NetworkSetupWindow(const char *title)
B_FOLLOW_LEFT_RIGHT | B_FOLLOW_TOP );
top_box->AddChild(line);
BuildProfilesMenu(profiles_menu, SELECT_PROFILE_MSG);
_BuildProfilesMenu(profiles_menu, SELECT_PROFILE_MSG);
r.top += 2 + V_MARGIN;
@@ -89,10 +87,9 @@ NetworkSetupWindow::NetworkSetupWindow(const char *title)
// Make the show popup field half the whole width and centered
menu_field = new BMenuField(r, "show_menu", SHOW_LABEL, show_menu);
menu_field->SetFont(be_plain_font);
menu_field->SetDivider(be_plain_font->StringWidth(SHOW_LABEL "#"));
menu_field->SetFont(be_bold_font);
menu_field->SetDivider(be_bold_font->StringWidth(SHOW_LABEL "#"));
top_box->AddChild(menu_field);
// menu_field->SetViewColor((rand() % 256), (rand() % 256), (rand() % 256));
menu_field->ResizeToPreferred();
menu_field->GetPreferredSize(&w, &h);
@@ -109,7 +106,6 @@ NetworkSetupWindow::NetworkSetupWindow(const char *title)
top_box->ResizeTo(Bounds().Width(), r.bottom + 1 + V_MARGIN);
// ---- Bottom globals buttons section
r = Bounds();
r.top = top_box->Frame().bottom + 1;
bottom_box = new BBox(r, NULL, B_FOLLOW_NONE,
@@ -144,9 +140,9 @@ NetworkSetupWindow::NetworkSetupWindow(const char *title)
size += SMALL_MARGIN + w;
button = new BButton(r, "revert", REVERT_LABEL,
new BMessage(REVERT_MSG),
B_FOLLOW_TOP | B_FOLLOW_RIGHT);
button = new BButton(r, "revert", REVERT_LABEL, new BMessage(REVERT_MSG),
B_FOLLOW_TOP | B_FOLLOW_RIGHT);
button->GetPreferredSize(&w, &h);
button->ResizeToPreferred();
button->MoveTo(x - w - SMALL_MARGIN, r.top);
@@ -180,29 +176,24 @@ NetworkSetupWindow::NetworkSetupWindow(const char *title)
}
// --------------------------------------------------------------
NetworkSetupWindow::~NetworkSetupWindow()
{
}
// --------------------------------------------------------------
bool NetworkSetupWindow::QuitRequested()
bool
NetworkSetupWindow::QuitRequested()
{
be_app->PostMessage(B_QUIT_REQUESTED);
return true;
}
// --------------------------------------------------------------
void NetworkSetupWindow::MessageReceived
(
BMessage * msg
)
void
NetworkSetupWindow::MessageReceived(BMessage* msg)
{
switch (msg->what) {
/*
case NEW_PROFILE_MSG:
break;
@@ -210,18 +201,9 @@ void NetworkSetupWindow::MessageReceived
break;
case DELETE_PROFILE_MSG: {
BString text;
text << "Are you sure you want to remove '";
text << fProfilesMenu->MenuItem()->Label();
text << "' profile?";
BAlert *alert = new BAlert("Hum...", text.String() ,"Cancel", "Delete",
NULL, B_WIDTH_AS_USUAL, B_OFFSET_SPACING, B_WARNING_ALERT);
alert->SetShortcut(0, B_ESCAPE);
alert->Go();
break;
}
*/
case SELECT_PROFILE_MSG: {
BPath name;
const char *path;
@@ -249,25 +231,21 @@ void NetworkSetupWindow::MessageReceived
break;
fPanel->AddChild(fAddonView);
fAddonView->ResizeTo(fPanel->Bounds().Width(), fPanel->Bounds().Height());
// fAddonView->SetViewColor((rand() % 256), (rand() % 256), (rand() % 256));
fAddonView->ResizeTo(fPanel->Bounds().Width(),
fPanel->Bounds().Height());
break;
}
default:
inherited::MessageReceived(msg);
};
}
}
// --------------------------------------------------------------
void NetworkSetupWindow::BuildProfilesMenu
(
BMenu *menu,
int32 msg_what
)
void
NetworkSetupWindow::_BuildProfilesMenu(BMenu* menu, int32 msg_what)
{
BMenuItem * item;
BMenuItem* item;
char current_profile[256] = { 0 };
menu->SetRadioMode(true);
@@ -276,7 +254,7 @@ void NetworkSetupWindow::BuildProfilesMenu
if (dir.InitCheck() == B_OK) {
BEntry entry;
BMessage *msg;
BMessage* msg;
dir.Rewind();
while (dir.GetNextEntry(&entry) >= 0) {
@@ -303,76 +281,52 @@ void NetworkSetupWindow::BuildProfilesMenu
item = new BMenuItem(name.Leaf(), msg);
menu->AddItem(item);
};
};
/*
menu->AddSeparatorItem();
}
}
menu->AddSeparatorItem();
menu->AddItem(new BMenuItem(NEW_PROFILE_LABEL,
new BMessage(NEW_PROFILE_MSG)));
menu->AddItem(new BMenuItem(DELETE_PROFILE_LABEL,
new BMessage(DELETE_PROFILE_MSG)));
menu->AddItem(new BMenuItem(NEW_PROFILE_LABEL, new BMessage(NEW_PROFILE_MSG)));
menu->AddItem(new BMenuItem(RENAME_PROFILE_LABEL, new BMessage(RENAME_PROFILE_MSG)));
menu->AddItem(new BMenuItem(DELETE_PROFILE_LABEL, new BMessage(DELETE_PROFILE_MSG)));
*/
if (strlen(current_profile)) {
item = menu->FindItem(current_profile);
if (item) {
BString label;
// bool is_default = (strcmp(current_profile, "default") == 0);
label << item->Label();
label << " (current)";
item->SetLabel(label.String());
item->SetMarked(true);
// fDeleteProfileButton->SetEnabled(!is_default);
};
};
}
}
}
// --------------------------------------------------------------
void NetworkSetupWindow::BuildShowMenu
(
BMenu *menu,
int32 msg_what
)
void
NetworkSetupWindow::_BuildShowMenu(BMenu* menu, int32 msg_what)
{
menu->SetRadioMode(true);
menu->AddItem(new BMenuItem("Status", new BMessage(msg_what)));
menu->AddSeparatorItem();
/*
menu->AddItem(item = new BMenuItem("vt86c100/0 interface", 0));
item->SetMarked(true);
menu->AddItem(item = new BMenuItem("rtl8136/0 interface", 0));
menu->AddItem(item = new BMenuItem("Dialup", 0));
menu->AddItem(item = new BMenuItem("Identity", 0));
menu->AddItem(item = new BMenuItem("Services", 0));
*/
menu->SetRadioMode(true);
BPath path;
BPath addon_path;
BDirectory dir;
BEntry entry;
char * search_paths;
char * search_path;
char * next_path_token;
search_paths = getenv("ADDON_PATH");
char* search_paths = getenv("ADDON_PATH");
if (!search_paths)
// Nowhere to search addons!!!
return;
fMinAddonViewRect.Set(0, 0, 200, 200); // Minimum size
search_paths = strdup(search_paths);
search_path = strtok_r(search_paths, ":", &next_path_token);
search_paths = strdup(search_paths);
char* next_path_token;
char* search_path = strtok_r(search_paths, ":", &next_path_token);
while (search_path) {
if (strncmp(search_path, "%A/", 3) == 0) {
// compute "%A/..." path
app_info ai;
app_info ai;
be_app->GetAppInfo(&ai);
entry.SetTo(&ai.ref);
entry.GetPath(&path);
@@ -381,12 +335,9 @@ void NetworkSetupWindow::BuildShowMenu
} else {
path.SetTo(search_path);
path.Append("network_setup");
// path.Append("boneyard");
};
}
search_path = strtok_r(NULL, ":", &next_path_token);
printf("Looking into %s\n", path.Path());
dir.SetTo(path.Path());
if (dir.InitCheck() != B_OK)
@@ -400,27 +351,23 @@ void NetworkSetupWindow::BuildShowMenu
entry.GetPath(&addon_path);
image_id addon_id = load_add_on(addon_path.Path());
if (addon_id < 0) {
printf("Failed to load %s addon: %s.\n", addon_path.Path(), strerror(addon_id));
printf("Failed to load %s addon: %s.\n", addon_path.Path(),
strerror(addon_id));
continue;
};
printf("Addon %s loaded.\n", addon_path.Path());
by_instantiate_func by_instantiate;
}
network_setup_addon_instantiate get_nth_addon;
status_t status;
status = get_image_symbol(addon_id, "get_nth_addon", B_SYMBOL_TYPE_TEXT, (void **) &get_nth_addon);
status_t status = get_image_symbol(addon_id, "get_nth_addon",
B_SYMBOL_TYPE_TEXT, (void **) &get_nth_addon);
if (status == B_OK) {
NetworkSetupAddOn *addon;
int n;
n = 0;
int n = 0;
while ((addon = get_nth_addon(addon_id, n)) != NULL) {
BMessage *msg = new BMessage(msg_what);
BMessage* msg = new BMessage(msg_what);
BRect r(0, 0, 0, 0);
BView * addon_view = addon->CreateView(&r);
BView* addon_view = addon->CreateView(&r);
fMinAddonViewRect = fMinAddonViewRect | r;
msg->AddInt32("image_id", addon_id);
@@ -430,38 +377,15 @@ void NetworkSetupWindow::BuildShowMenu
menu->AddItem(new BMenuItem(addon->Name(), msg));
n++;
}
continue; // skip the Boneyard addon test...
};
status = get_image_symbol(addon_id, "instantiate", B_SYMBOL_TYPE_TEXT, (void **) &by_instantiate);
if (status == B_OK) {
BYAddon *addon;
addon = by_instantiate();
BRect r(0, 0, 0, 0);
BView * addon_view = addon->CreateView(&r);
fMinAddonViewRect = fMinAddonViewRect | r;
BMessage *msg = new BMessage(msg_what);
msg->AddInt32("image_id", addon_id);
msg->AddString("addon_path", addon_path.Path());
msg->AddPointer("byaddon", addon);
msg->AddPointer("addon_view", addon_view);
menu->AddItem(new BMenuItem(addon->Name(), msg));
continue;
};
}
// No "addon instantiate function" symbol found in this addon
printf("No symbol \"get_nth_addon\" or \"instantiate\" not found in %s addon: not a network setup addon!\n", addon_path.Path());
printf("No symbol \"get_nth_addon\" found in %s addon: not a "
"network setup addon!\n", addon_path.Path());
unload_add_on(addon_id);
};
};
}
}
free(search_paths);
menu->AddItem(new BMenuItem("Very long label of network stuff to set/display", new BMessage(msg_what)));
}
+18 -24
View File
@@ -9,28 +9,24 @@
#define COPY_PROFILE_LABEL "Copy" B_UTF8_ELLIPSIS
#define DELETE_PROFILE_LABEL "Delete"
#define MANAGE_PROFILES_LABEL "Manage profiles" B_UTF8_ELLIPSIS
#define MANAGE_PROFILES_LABEL "Manage profiles" B_UTF8_ELLIPSIS
#define SHOW_LABEL "Show:"
#define SHOW_LABEL "Show:"
#define DONT_TOUCH_LABEL "Prevent unwanted changes"
#define SAVE_LABEL "Save"
#define HELP_LABEL "Help"
#define REVERT_LABEL "Revert"
#define APPLY_NOW_LABEL "Apply Now"
#define DONT_TOUCH_LABEL "Prevent unwanted changes"
#define SAVE_LABEL "Save"
#define HELP_LABEL "Help"
#define REVERT_LABEL "Revert"
#define APPLY_NOW_LABEL "Apply Now"
class NetworkSetupWindow : public BWindow
{
public:
// Constructors, destructors, operators...
NetworkSetupWindow(const char *title);
~NetworkSetupWindow();
typedef BWindow inherited;
// Virtual function overrides
// public constantes
enum {
SELECT_PROFILE_MSG = 'prof',
MANAGE_PROFILES_MSG = 'mngp',
@@ -45,21 +41,19 @@ class NetworkSetupWindow : public BWindow
};
bool QuitRequested();
void MessageReceived(BMessage * msg);
// From here, it's none of your business! ;-)
private:
void BuildProfilesMenu(BMenu *menu, int32 msg);
void BuildShowMenu(BMenu *menu, int32 msg);
BButton * fHelpButton;
BButton * fRevertButton;
BButton * fApplyNowButton;
void MessageReceived(BMessage* msg);
BBox * fPanel;
BView * fAddonView;
private:
void _BuildProfilesMenu(BMenu* menu, int32 msg);
void _BuildShowMenu(BMenu* menu, int32 msg);
BButton* fHelpButton;
BButton* fRevertButton;
BButton* fApplyNowButton;
BBox* fPanel;
BView* fAddonView;
BRect fMinAddonViewRect;
};
#endif // ifdef NETWORKSETUPWINDOW_H
@@ -1,447 +0,0 @@
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <app/Application.h>
#include <app/Roster.h>
#include <InterfaceKit.h>
#include <StorageKit.h>
#include <SupportKit.h>
#include "BoneyardAddOn.h"
#include "NetworkSetupAddOn.h"
#include "NetworkWindow.h"
// --------------------------------------------------------------
NetworkWindow::NetworkWindow(const char *title)
: BWindow(BRect(100, 100, 600, 600), title, B_TITLED_WINDOW,
B_ASYNCHRONOUS_CONTROLS | B_NOT_ZOOMABLE)
{
BMenu *menu;
BBox *box, *bb;
BButton *button;
BRect r;
float w, h, divider;
// float min_w, min_h;
#define H_MARGIN 12
#define V_MARGIN 12
#define LINE_MARGIN 4
divider = MAX(be_bold_font->StringWidth(PROFILE_LABEL "#"),
be_bold_font->StringWidth(SHOW_LABEL "#"));
box = new BBox(Bounds(), NULL, B_FOLLOW_ALL,
B_WILL_DRAW | B_FRAME_EVENTS | B_NAVIGABLE_JUMP,
B_PLAIN_BORDER);
AddChild(box);
r = box->Bounds();
r.InsetBy(H_MARGIN, V_MARGIN);
// ---- Profiles section
menu = new BPopUpMenu("<none>");
fProfilesMenu = new BMenuField(r, "profiles_menu", PROFILE_LABEL, menu);
fProfilesMenu->SetFont(be_bold_font);
fProfilesMenu->SetDivider(divider);
box->AddChild(fProfilesMenu);
fProfilesMenu->ResizeToPreferred();
fProfilesMenu->GetPreferredSize(&w, &h);
BuildProfilesMenu(menu, SELECT_PROFILE_MSG);
button = new BButton(r, "apply_now", APPLY_NOW_LABEL,
new BMessage(APPLY_NOW_MSG),
B_FOLLOW_TOP | B_FOLLOW_RIGHT);
button->GetPreferredSize(&w, &h);
button->ResizeToPreferred();
button->MoveBy(r.right - w - H_MARGIN, 0);
box->AddChild(button);
fApplyButton = button;
r.top = button->Frame().bottom + V_MARGIN;
// ---- Show settings section
bb = new BBox(r, "show_box", B_FOLLOW_ALL,
B_WILL_DRAW | B_FRAME_EVENTS | B_NAVIGABLE_JUMP,
B_FANCY_BORDER);
box->AddChild(bb);
menu = new BPopUpMenu("<nothing>");
fShowMenu = new BMenuField(r, "show_menu", SHOW_LABEL, menu,
B_FOLLOW_TOP | B_FOLLOW_LEFT,
B_WILL_DRAW | B_FRAME_EVENTS | B_NAVIGABLE);
// fShowMenu->SetFont(be_bold_font);
// fShowMenu->SetDivider(be_bold_font->StringWidth(SHOW_LABEL "#"));
fShowMenu->SetDivider(be_plain_font->StringWidth(SHOW_LABEL "#"));
bb->SetLabel(fShowMenu);
fShowMenu->ResizeToPreferred();
fShowMenu->GetPreferredSize(&w, &h);
BuildShowMenu(menu, SHOW_MSG);
r = bb->Bounds();
r.top += h / 2;
r.InsetBy(H_MARGIN, V_MARGIN);
fPanel = new BBox(r, "showview_box", B_FOLLOW_ALL,
B_WILL_DRAW | B_FRAME_EVENTS | B_NAVIGABLE_JUMP,
B_NO_BORDER);
bb->AddChild(fPanel);
fShowRect = fPanel->Bounds();
fShowView = NULL;
}
// --------------------------------------------------------------
NetworkWindow::~NetworkWindow()
{
}
// --------------------------------------------------------------
bool NetworkWindow::QuitRequested()
{
be_app->PostMessage(B_QUIT_REQUESTED);
return true;
}
// --------------------------------------------------------------
void NetworkWindow::MessageReceived
(
BMessage * msg
)
{
switch (msg->what) {
case NEW_PROFILE_MSG:
break;
case RENAME_PROFILE_MSG:
break;
case DELETE_PROFILE_MSG: {
BString text;
text << "Are you sure you want to remove '";
text << fProfilesMenu->MenuItem()->Label();
text << "' configuration?";
BAlert *alert = new BAlert("Hum...", text.String() ,"Cancel", "Delete",
NULL, B_WIDTH_AS_USUAL, B_OFFSET_SPACING, B_WARNING_ALERT);
alert->SetShortcut(0, B_ESCAPE);
alert->Go();
break;
}
case SELECT_PROFILE_MSG: {
BPath name;
const char *path;
bool is_default;
BMenuItem *item;
BMenu *menu;
if (msg->FindString("path", &path) != B_OK)
break;
name.SetTo(path);
is_default = (strcmp(name.Leaf(), "default") == 0);
menu = fProfilesMenu->Menu();
item = menu->FindItem(RENAME_PROFILE_LABEL);
if (item)
item->SetEnabled(!is_default);
item = menu->FindItem(DELETE_PROFILE_LABEL);
if (item)
item->SetEnabled(!is_default);
break;
}
case SHOW_MSG: {
BYAddon *by;
NetworkSetupAddOn *addon;
if (fShowView)
fShowView->RemoveSelf();
fShowView = NULL;
by = NULL;
addon = NULL;
if (msg->FindPointer("addon", (void **) &addon) != B_OK) {
if (msg->FindPointer("byaddon", (void **) &by) != B_OK)
break;
};
fShowRect = fPanel->Bounds();
if (addon)
fShowView = addon->CreateView(&fShowRect);
else
fShowView = by->CreateView(&fShowRect);
if (fShowView) {
fPanel->AddChild(fShowView);
// fShowView->SetViewColor((rand() % 256), (rand() % 256), (rand() % 256));
fShowView->ResizeTo(fPanel->Bounds().Width(), fPanel->Bounds().Height());
};
break;
}
default:
inherited::MessageReceived(msg);
};
}
// --------------------------------------------------------------
void NetworkWindow::BuildProfilesMenu
(
BMenu *menu,
int32 msg_what
)
{
BMenuItem * item;
char current_profile[256] = { 0 };
menu->SetRadioMode(true);
BDirectory dir("/etc/network/profiles");
if (dir.InitCheck() == B_OK) {
BEntry entry;
BMessage *msg;
dir.Rewind();
while (dir.GetNextEntry(&entry) >= 0) {
BPath name;
entry.GetPath(&name);
if (entry.IsSymLink() &&
strcmp("current", name.Leaf()) == 0) {
BSymLink symlink(&entry);
if (symlink.IsAbsolute())
// oh oh, sorry, wrong symlink...
continue;
symlink.ReadLink(current_profile, sizeof(current_profile));
continue;
};
if (!entry.IsDirectory())
continue;
msg = new BMessage(msg_what);
msg->AddString("path", name.Path());
item = new BMenuItem(name.Leaf(), msg);
menu->AddItem(item);
};
};
menu->AddSeparatorItem();
menu->AddItem(new BMenuItem(NEW_PROFILE_LABEL, new BMessage(NEW_PROFILE_MSG)));
menu->AddItem(new BMenuItem(RENAME_PROFILE_LABEL, new BMessage(RENAME_PROFILE_MSG)));
menu->AddItem(new BMenuItem(DELETE_PROFILE_LABEL, new BMessage(DELETE_PROFILE_MSG)));
if (strlen(current_profile)) {
item = menu->FindItem(current_profile);
if (item) {
BString label;
bool is_default = (strcmp(current_profile, "default") == 0);
label << item->Label();
label << " (current)";
item->SetLabel(label.String());
item->SetMarked(true);
item = menu->FindItem(RENAME_PROFILE_LABEL);
if (item)
item->SetEnabled(!is_default);
item = menu->FindItem(DELETE_PROFILE_LABEL);
if (item)
item->SetEnabled(!is_default);
};
};
}
// --------------------------------------------------------------
void NetworkWindow::BuildShowMenu
(
BMenu *menu,
int32 msg_what
)
{
menu->SetRadioMode(true);
/*
menu->AddItem(item = new BMenuItem("vt86c100/0 interface", 0));
item->SetMarked(true);
menu->AddItem(item = new BMenuItem("rtl8136/0 interface", 0));
menu->AddItem(item = new BMenuItem("Dialup", 0));
menu->AddItem(item = new BMenuItem("Identity", 0));
menu->AddItem(item = new BMenuItem("Services", 0));
*/
BPath path;
BPath addon_path;
BDirectory dir;
BEntry entry;
char * search_paths;
char * search_path;
char * next_path_token;
search_paths = getenv("ADDON_PATH");
if (!search_paths)
// Nowhere to search addons!!!
return;
search_paths = strdup(search_paths);
search_path = strtok_r(search_paths, ":", &next_path_token);
while (search_path) {
if (strncmp(search_path, "%A/", 3) == 0) {
// compute "%A/..." path
app_info ai;
be_app->GetAppInfo(&ai);
entry.SetTo(&ai.ref);
entry.GetPath(&path);
path.GetParent(&path);
path.Append(search_path + 3);
} else {
path.SetTo(search_path);
path.Append("boneyard");
};
search_path = strtok_r(NULL, ":", &next_path_token);
printf("Looking into %s\n", path.Path());
dir.SetTo(path.Path());
if (dir.InitCheck() != B_OK)
continue;
dir.Rewind();
while (dir.GetNextEntry(&entry) >= 0) {
if (entry.IsDirectory())
continue;
entry.GetPath(&addon_path);
image_id addon_id = load_add_on(addon_path.Path());
if (addon_id < 0) {
printf("Failed to load %s addon: %s.\n", addon_path.Path(), strerror(addon_id));
continue;
};
printf("Addon %s loaded.\n", addon_path.Path());
by_instantiate_func by_func;
network_setup_addon_instantiate ns_func;
status_t status;
status = get_image_symbol(addon_id, "get_addon", B_SYMBOL_TYPE_TEXT, (void **) &ns_func);
if (status == B_OK) {
NetworkSetupAddOn *addon;
addon = ns_func();
BMessage *msg = new BMessage(msg_what);
msg->AddInt32("image_id", addon_id);
msg->AddString("addon_path", addon_path.Path());
msg->AddPointer("addon", addon);
menu->AddItem(new BMenuItem(addon->Name(), msg));
continue;
};
status = get_image_symbol(addon_id, "instantiate", B_SYMBOL_TYPE_TEXT, (void **) &by_func);
if (status == B_OK) {
BYAddon *addon;
addon = by_func();
BMessage *msg = new BMessage(msg_what);
msg->AddInt32("image_id", addon_id);
msg->AddString("addon_path", addon_path.Path());
msg->AddPointer("byaddon", addon);
menu->AddItem(new BMenuItem(addon->Name(), msg));
continue;
};
// No "modules" symbol found in this addon
printf("Symbol \"instantiate\" not found in %s addon: not a module addon!\n", addon_path.Path());
unload_add_on(addon_id);
};
};
free(search_paths);
menu->AddSeparatorItem();
menu->AddItem(new BMenuItem("Status", new BMessage(msg_what)));
menu->AddItem(new BMenuItem("Very long label of network stuff to set/display", new BMessage(msg_what)));
}
// #pragma mark Boneyard add-ons support
_EXPORT void boneyard_do_save() {}
_EXPORT void boneyard_do_revert() {}
BYDataEntry::BYDataEntry(const char *name, const char *value, const char *comment)
{
m_name = (char *) name;
m_value = (char *) value;
m_comment = (char *) comment;
}
BYDataEntry::~BYDataEntry() {}
const char * BYDataEntry::Name() { return m_name; }
const char * BYDataEntry::Value() { return m_value; }
const char * BYDataEntry::Comment() { return m_comment; }
void BYDataEntry::SetValue(char *value) { m_value = value; }
void BYDataEntry::SetComment(char *comment) { m_comment = comment; }
void BYDataEntry::_ReservedDataEntry1() {}
void BYDataEntry::_ReservedDataEntry2() {}
BYAddon::BYAddon() {}
BYAddon::~BYAddon() {}
BView * BYAddon::CreateView(BRect *bounds) { return NULL; }
void BYAddon::Revert() {}
void BYAddon::Save() {}
const char *BYAddon::Name() { return "noname"; }
const char *BYAddon::Section() { return "noname"; }
const char *BYAddon::Description() { return "noname"; }
const BList *BYAddon::FileList() { return NULL; }
int BYAddon::Importance() { return 10; }
const BList *BYAddon::ObtainSectionData() { return NULL; } // get all BYDataEntrys for my section.
const char *BYAddon::GetValue(const char *name) { return ""; } // get a value from your section.
void BYAddon::SetValue(const char *name,const char *data) {} // set a value in your section.
void BYAddon::ClearValue(const char *name) {} // remove an entry from your section.
void BYAddon::ClearSectionData() {} // remove all entries from your section.
bool BYAddon::IsDirty() { return false; } // query dirty status
void BYAddon::SetDirty(bool _dirty) {} // set dirty status
const BList *BYAddon::GetAddonList() { return NULL; } // get all add-ons in the cradle.
void BYAddon::_ReservedAddon1() {}
void BYAddon::_ReservedAddon2() {}
void BYAddon::_ReservedAddon3() {}
void BYAddon::_ReservedAddon4() {}
void BYAddon::_ReservedAddon5() {}
void BYAddon::_ReservedAddon6() {}
void BYAddon::_ReservedAddon7() {}
void BYAddon::_ReservedAddon8() {}
// void BYAddon::GetAddonList();
void save_config();
@@ -1,58 +0,0 @@
#ifndef NETWORKWINDOW_H
#define NETWORKWINDOW_H
#include <InterfaceKit.h>
#define PROFILE_LABEL "Settings profile:"
#define NEW_PROFILE_LABEL "New" B_UTF8_ELLIPSIS
#define RENAME_PROFILE_LABEL "Rename" B_UTF8_ELLIPSIS
#define DELETE_PROFILE_LABEL "Delete"
#define SHOW_LABEL " Show:"
#define SAVE_LABEL "Save"
#define APPLY_NOW_LABEL "Apply Now"
class NetworkWindow : public BWindow
{
public:
// Constructors, destructors, operators...
NetworkWindow(const char *title);
~NetworkWindow();
typedef BWindow inherited;
// Virtual function overrides
public:
// public constantes
enum
{
SELECT_PROFILE_MSG = 'prof',
NEW_PROFILE_MSG = 'newp',
RENAME_PROFILE_MSG = 'renp',
DELETE_PROFILE_MSG = 'delp',
SHOW_MSG = 'dest',
APPLY_NOW_MSG = 'strt'
};
virtual bool QuitRequested();
virtual void MessageReceived(BMessage * msg);
// From here, it's none of your business! ;-)
private:
void BuildProfilesMenu(BMenu *menu, int32 msg);
void BuildShowMenu(BMenu *menu, int32 msg);
BBox *fPanel;
BMenuField *fProfilesMenu;
BMenuField *fShowMenu;
BButton *fRenameButton;
BButton *fDeleteButton;
BButton *fApplyButton;
BRect fShowRect;
BView *fShowView;
};
#endif // ifdef NETWORKWINDOW_H
Binary file not shown.
@@ -0,0 +1,10 @@
SubDir HAIKU_TOP src tests kits net preflet ServicesAddOn ;
UseHeaders [ FDirName $(HAIKU_TOP) src tests kits net preflet ] ;
Addon Services : network_setup :
ServicesAddOn.cpp
;
LinkSharedOSLibs Services : <installed>Network_Setup be ;
@@ -0,0 +1,104 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ListView.h>
#include <ScrollView.h>
#include <String.h>
#include "NetworkSetupAddOn.h"
class ServicesAddOn : public NetworkSetupAddOn {
public:
ServicesAddOn(image_id addon_image);
BView* CreateView(BRect* bounds);
const char* Name() { return "Internet services"; };
};
NetworkSetupAddOn*
get_nth_addon(image_id image, int index)
{
if (index != 0)
return NULL;
return new ServicesAddOn(image);
}
// #pragma mark -
ServicesAddOn::ServicesAddOn(image_id image)
:
NetworkSetupAddOn(image)
{
}
BView*
ServicesAddOn::CreateView(BRect* bounds)
{
BRect r = *bounds;
if (r.Width() < 100 || r.Height() < 100)
r.Set(0, 0, 100, 100);
BRect rlv = r.InsetByCopy(2, 2);
rlv.right -= B_V_SCROLL_BAR_WIDTH;
BListView* lv = new BListView(rlv, "inetd_services",
B_SINGLE_SELECTION_LIST, B_FOLLOW_ALL_SIDES);
BScrollView* sv = new BScrollView( "inetd_services_scrollview", lv,
B_FOLLOW_ALL_SIDES, B_WILL_DRAW | B_FRAME_EVENTS, false, true);
FILE *f = fopen("/etc/inetd.conf", "r");
if (f) {
char line[1024], *l;
char *token;
while (fgets(line, sizeof(line), f)) {
l = line;
if (! *l)
continue;
if (line[0] == '#') {
if (line[1] == ' ' || line[1] == '\t' ||
line[1] == '\0' || line[1] == '\n' ||
line[1] == '\r')
// skip comments
continue;
l++; // jump the disable/comment service mark
}
BString label;
token = strtok(l, " \t"); // service name
label << token;
token = strtok(NULL, " \t"); // type
label << " (" << token << ")";
token = strtok(NULL, " \t"); // protocol
label << " " << token;
lv->AddItem(new BStringItem(label.String()));
}
fclose(f);
}
*bounds = r;
return sv;
}
/*
BDirectory folder;
BEntry entry;
folder.SetTo ( "/boot/beos/etc/bubblejet" );
if ( folder.InitCheck() != B_OK )
return;
while ( folder.GetNextEntry ( &entry ) != B_ENTRY_NOT_FOUND )
{
char name[B_FILE_NAME_LENGTH];
if ( entry.GetName(name) == B_NO_ERROR )
m_model_list->AddItem (new BStringItem(name));
};
m_model_list->SetSelectionMessage(new BMessage(MODEL_MSG));
m_model_list->SetInvocationMessage(new BMessage(OK_MSG));
*/
+1
View File
@@ -0,0 +1 @@
../NetworkSetup
@@ -0,0 +1,456 @@
/*
* Copyright 2004-2008 Haiku Inc. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Authors:
* Andre Alves Garzia, andre@andregarzia.com
* Stephan Assmuß
* Axel Dörfler
* Fredrik Modéen
* Hugo Santos
* Philippe Saint-Pierre
*/
#include "EthernetSettingsView.h"
#include "Setting.h"
#include <InterfaceKit.h>
#include <GridView.h>
#include <GroupView.h>
#include <LayoutItem.h>
#include <SpaceLayoutItem.h>
#include <File.h>
#include <Path.h>
#include <Directory.h>
#include <FindDirectory.h>
#include <errno.h>
#include <stdio.h>
#include <NetServer.h>
#include <support/Beep.h>
static const uint32 kMsgApply = 'aply';
static const uint32 kMsgRevert = 'rvrt';
static const uint32 kMsgClose = 'clse';
static const uint32 kMsgField = 'fild';
static const uint32 kMsgMode = 'mode';
static const uint32 kMsgChange = 'chng';
static void
SetupTextControl(BTextControl *control)
{
// TODO: Disallow characters, etc.
// Would be nice to have a real
// formatted input control
control->SetModificationMessage(new BMessage(kMsgChange));
}
// #pragma mark -
EthernetSettingsView::EthernetSettingsView(Setting* setting)
: BView("EthernetSettingsView", 0, NULL),
fCurrentSettings(setting)
{
SetViewColor(ui_color(B_PANEL_BACKGROUND_COLOR));
// build the GUI
BGroupLayout* rootLayout = new BGroupLayout(B_VERTICAL);
SetLayout(rootLayout);
BGridView* controlsGroup = new BGridView();
BGridLayout* layout = controlsGroup->GridLayout();
// insets
float inset = ceilf(be_plain_font->Size() * 0.7);
rootLayout->SetInsets(inset, inset, inset, inset);
rootLayout->SetSpacing(inset);
layout->SetSpacing(inset, inset);
BPopUpMenu* modeMenu = new BPopUpMenu("modes");
modeMenu->AddItem(new BMenuItem("Static", new BMessage(kMsgMode)));
modeMenu->AddItem(new BMenuItem("DHCP", new BMessage(kMsgMode)));
fTypeMenuField = new BMenuField("Mode:", modeMenu);
layout->AddItem(fTypeMenuField->CreateLabelLayoutItem(), 0, 1);
layout->AddItem(fTypeMenuField->CreateMenuBarLayoutItem(), 1, 1);
fIPTextControl = new BTextControl("IP Address:", "", NULL);
SetupTextControl(fIPTextControl);
BLayoutItem* layoutItem = fIPTextControl->CreateTextViewLayoutItem();
layoutItem->SetExplicitMinSize(BSize(
fIPTextControl->StringWidth("XXX.XXX.XXX.XXX") + inset,
B_SIZE_UNSET));
layout->AddItem(fIPTextControl->CreateLabelLayoutItem(), 0, 2);
layout->AddItem(layoutItem, 1, 2);
fNetMaskTextControl = new BTextControl("Netmask:", "", NULL);
SetupTextControl(fNetMaskTextControl);
layout->AddItem(fNetMaskTextControl->CreateLabelLayoutItem(), 0, 3);
layout->AddItem(fNetMaskTextControl->CreateTextViewLayoutItem(), 1, 3);
fGatewayTextControl = new BTextControl("Gateway:", "", NULL);
SetupTextControl(fGatewayTextControl);
layout->AddItem(fGatewayTextControl->CreateLabelLayoutItem(), 0, 4);
layout->AddItem(fGatewayTextControl->CreateTextViewLayoutItem(), 1, 4);
// TODO: Replace the DNS text controls by a BListView with add/remove
// functionality and so on...
fPrimaryDNSTextControl = new BTextControl("DNS #1:", "", NULL);
SetupTextControl(fPrimaryDNSTextControl);
layout->AddItem(fPrimaryDNSTextControl->CreateLabelLayoutItem(), 0, 5);
layout->AddItem(fPrimaryDNSTextControl->CreateTextViewLayoutItem(), 1, 5);
fSecondaryDNSTextControl = new BTextControl("DNS #2:", "", NULL);
SetupTextControl(fSecondaryDNSTextControl);
layout->AddItem(fSecondaryDNSTextControl->CreateLabelLayoutItem(), 0, 6);
layout->AddItem(fSecondaryDNSTextControl->CreateTextViewLayoutItem(), 1, 6);
fErrorMessage = new BStringView("error", "");
fErrorMessage->SetAlignment(B_ALIGN_LEFT);
fErrorMessage->SetFont(be_bold_font);
fErrorMessage->SetExplicitMaxSize(BSize(B_SIZE_UNLIMITED, B_SIZE_UNSET));
layout->AddView(fErrorMessage, 1, 7);
// button group (TODO: move to window, but take care of
// enabling/disabling)
BGroupView* buttonGroup = new BGroupView(B_HORIZONTAL);
fRevertButton = new BButton("Revert", new BMessage(kMsgRevert));
fRevertButton->SetEnabled(false);
buttonGroup->GroupLayout()->AddView(fRevertButton);
buttonGroup->GroupLayout()->AddItem(BSpaceLayoutItem::CreateGlue());
fApplyButton = new BButton("Apply", new BMessage(kMsgApply));
buttonGroup->GroupLayout()->AddView(fApplyButton);
rootLayout->AddView(controlsGroup);
rootLayout->AddView(buttonGroup);
}
EthernetSettingsView::~EthernetSettingsView()
{
close(fSocket);
}
bool
EthernetSettingsView::_PrepareRequest(struct ifreq& request, const char* name)
{
// This function is used for talking direct to the stack.
// It's used by _ShowConfiguration.
if (strlen(name) > IF_NAMESIZE)
return false;
strcpy(request.ifr_name, name);
return true;
}
void
EthernetSettingsView::AttachedToWindow()
{
fApplyButton->SetTarget(this);
fRevertButton->SetTarget(this);
fIPTextControl->SetTarget(this);
fNetMaskTextControl->SetTarget(this);
fGatewayTextControl->SetTarget(this);
fPrimaryDNSTextControl->SetTarget(this);
fSecondaryDNSTextControl->SetTarget(this);
fTypeMenuField->Menu()->SetTargetForItems(this);
// display settigs of first adapter on startup
_ShowConfiguration(fCurrentSettings);
}
void
EthernetSettingsView::DetachedFromWindow()
{
}
void
EthernetSettingsView::_ShowConfiguration(Setting* setting)
{
// Clear the inputs.
fIPTextControl->SetText("");
fGatewayTextControl->SetText("");
fNetMaskTextControl->SetText("");
fPrimaryDNSTextControl->SetText("");
fSecondaryDNSTextControl->SetText("");
bool enableControls = false;
fTypeMenuField->SetEnabled(setting != NULL);
if (setting) {
fIPTextControl->SetText(setting->GetIP());
fGatewayTextControl->SetText(setting->GetGateway());
fNetMaskTextControl->SetText(setting->GetNetmask());
BMenuItem* item;
if (setting->GetAutoConfigure() == true)
item = fTypeMenuField->Menu()->FindItem("DHCP");
else
item = fTypeMenuField->Menu()->FindItem("Static");
if (item)
item->SetMarked(true);
enableControls = setting->GetAutoConfigure() == false;
if (setting->fNameservers.CountItems() >= 2) {
fSecondaryDNSTextControl->SetText(
setting->fNameservers.ItemAt(1)->String());
}
if (setting->fNameservers.CountItems() >= 1) {
fPrimaryDNSTextControl->SetText(
setting->fNameservers.ItemAt(0)->String());
}
}
//We don't want to enable loop
if (strcmp(fCurrentSettings->GetName(), "loop") == 0) {
_EnableTextControls(false);
fTypeMenuField->SetEnabled(false);
} else
_EnableTextControls(enableControls);
}
void
EthernetSettingsView::_EnableTextControls(bool enable)
{
fIPTextControl->SetEnabled(enable);
fGatewayTextControl->SetEnabled(enable);
fNetMaskTextControl->SetEnabled(enable);
fPrimaryDNSTextControl->SetEnabled(enable);
fSecondaryDNSTextControl->SetEnabled(enable);
}
void
EthernetSettingsView::_ApplyControlsToConfiguration()
{
if (!fCurrentSettings)
return;
fCurrentSettings->SetIP(fIPTextControl->Text());
fCurrentSettings->SetNetmask(fNetMaskTextControl->Text());
fCurrentSettings->SetGateway(fGatewayTextControl->Text());
fCurrentSettings->SetAutoConfigure(
strcmp(fTypeMenuField->Menu()->FindMarked()->Label(), "DHCP") == 0);
fCurrentSettings->fNameservers.MakeEmpty();
fCurrentSettings->fNameservers.AddItem(new BString(
fPrimaryDNSTextControl->Text()));
fCurrentSettings->fNameservers.AddItem(new BString(
fSecondaryDNSTextControl->Text()));
fApplyButton->SetEnabled(false);
fRevertButton->SetEnabled(true);
}
void
EthernetSettingsView::_SaveConfiguration()
{
_ApplyControlsToConfiguration();
_SaveDNSConfiguration();
_SaveAdaptersConfiguration();
if (fCurrentSettings->GetAutoConfigure())
_TriggerAutoConfig(fCurrentSettings->GetName());
}
void
EthernetSettingsView::_SaveDNSConfiguration()
{
BFile file("/etc/resolv.conf",
B_CREATE_FILE | B_ERASE_FILE | B_WRITE_ONLY);
if (file.InitCheck() < B_OK) {
fprintf(stderr, "failed to open /etc/resolv.conf for writing: %s\n",
strerror(file.InitCheck()));
return;
}
BString content("# Generated by Network Preflet\n");
for (int j = 0; j < fCurrentSettings->fNameservers.CountItems(); j++) {
if (fCurrentSettings->fNameservers.ItemAt(j)->Length() > 0) {
content << "nameserver\t"
<< fCurrentSettings->fNameservers.ItemAt(j)->String() << "\n";
}
}
file.Write(content.String(), content.Length());
}
void
EthernetSettingsView::_SaveAdaptersConfiguration()
{
BPath path;
status_t status = _GetPath("interfaces", path);
printf("Path = %s\n", path.Path());
if (status < B_OK)
return;
FILE* fp = NULL;
if (fCurrentSettings->GetAutoConfigure())
return;
if (fp == NULL) {
fp = fopen(path.Path(), "w");
if (fp == NULL) {
fprintf(stderr, "failed to open file %s to write "
"configuration: %s\n", path.Path(), strerror(errno));
return;
}
}
fprintf(fp, "interface %s {\n\t\taddress {\n",fCurrentSettings->GetName());
fprintf(fp, "\t\t\tfamily\tinet\n");
fprintf(fp, "\t\t\taddress\t%s\n",fCurrentSettings->GetIP());
fprintf(fp, "\t\t\tgateway\t%s\n",fCurrentSettings->GetGateway());
fprintf(fp, "\t\t\tmask\t%s\n",fCurrentSettings->GetNetmask());
fprintf(fp, "\t\t}\n}\n\n");
if (fp) {
printf("%s saved.\n", path.Path());
fclose(fp);
} else {
// all configuration is DHCP, so delete interfaces file.
remove(path.Path());
}
}
status_t
EthernetSettingsView::_TriggerAutoConfig(const char* device)
{
BMessenger networkServer(kNetServerSignature);
if (!networkServer.IsValid()) {
(new BAlert("error", "The net_server needs to run for the auto "
"configuration!", "Ok"))->Go();
return B_ERROR;
}
BMessage message(kMsgConfigureInterface);
message.AddString("device", device);
BMessage address;
address.AddString("family", "inet");
address.AddBool("auto_config", true);
message.AddMessage("address", &address);
BMessage reply;
status_t status = networkServer.SendMessage(&message, &reply);
if (status != B_OK) {
BString errorMessage("Sending auto-config message failed: ");
errorMessage << strerror(status);
(new BAlert("error", errorMessage.String(), "Ok"))->Go();
return status;
} else if (reply.FindInt32("status", &status) == B_OK
&& status != B_OK) {
BString errorMessage("Auto-configuring failed: ");
errorMessage << strerror(status);
(new BAlert("error", errorMessage.String(), "Ok"))->Go();
return status;
}
return B_OK;
}
status_t
EthernetSettingsView::_GetPath(const char* name, BPath& path)
{
if (find_directory(B_COMMON_SETTINGS_DIRECTORY, &path, true) != B_OK)
return B_ERROR;
path.Append("network");
create_directory(path.Path(), 0755);
if (name != NULL)
path.Append(name);
return B_OK;
}
bool
MatchPattern(const char* string, const char* pattern)
{
regex_t compiled;
bool result = regcomp(&compiled, pattern, REG_NOSUB | REG_EXTENDED) == 0
&& regexec(&compiled, string, 0, NULL, 0) == 0;
regfree(&compiled);
return result;
}
bool
EthernetSettingsView::_ValidateControl(BTextControl* control)
{
static const char* pattern = "^(25[0-5]|2[0-4][0-9]|[01][0-9]{2}|[0-9]"
"{1,2})(\\.(25[0-5]|2[0-4][0-9]|[01][0-9]{2}|[0-9]{1,2})){3}$";
if (control->IsEnabled() && !MatchPattern(control->Text(), pattern)) {
control->MakeFocus();
BString errorMessage;
errorMessage << control->Label();
errorMessage.RemoveLast(":");
errorMessage << " is invalid";
fErrorMessage->SetText(errorMessage.String());
beep();
return false;
}
return true;
}
void
EthernetSettingsView::MessageReceived(BMessage* message)
{
switch (message->what) {
case kMsgMode:
if (BMenuItem* item = fTypeMenuField->Menu()->FindMarked())
_EnableTextControls(strcmp(item->Label(), "DHCP") != 0);
fApplyButton->SetEnabled(true);
fRevertButton->SetEnabled(true);
break;
case kMsgRevert:
_ShowConfiguration(fCurrentSettings);
fRevertButton->SetEnabled(false);
break;
case kMsgApply:
if (_ValidateControl(fIPTextControl)
&& _ValidateControl(fNetMaskTextControl)
&& (strlen(fGatewayTextControl->Text()) == 0
|| _ValidateControl(fGatewayTextControl))
&& (strlen(fPrimaryDNSTextControl->Text()) == 0
|| _ValidateControl(fPrimaryDNSTextControl))
&& (strlen(fSecondaryDNSTextControl->Text()) == 0
|| _ValidateControl(fSecondaryDNSTextControl)))
_SaveConfiguration();
break;
case kMsgChange:
fErrorMessage->SetText("");
//We don't want to enable loop
if (strcmp(fCurrentSettings->GetName(), "loop") == 0)
fApplyButton->SetEnabled(false);
else
fApplyButton->SetEnabled(true);
break;
default:
BView::MessageReceived(message);
}
}
@@ -0,0 +1,78 @@
/*
* Copyright 2004-2007 Haiku Inc. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Author:
* Andre Alves Garzia, andre@andregarzia.com
* Axel Dörfler
* Fredrik Modéen
* Hugo Santos
*/
#ifndef ETHERNET_SETTINGS_VIEW_H
#define ETHERNET_SETTINGS_VIEW_H
#include "Setting.h"
#include <ObjectList.h>
#include <View.h>
#include <posix/regex.h>
class BButton;
class BMenuField;
class BPath;
class BTextControl;
class BStringView;
class EthernetSettingsView : public BView {
public:
EthernetSettingsView(Setting* setting);
virtual ~EthernetSettingsView();
virtual void MessageReceived(BMessage* message);
virtual void AttachedToWindow();
virtual void DetachedFromWindow();
void SaveProfile(BString profileName);
void LoadProfile(BString profileName);
private:
bool _PrepareRequest(struct ifreq& request,
const char* name);
void _ShowConfiguration(Setting* setting);
void _EnableTextControls(bool enable);
void _SaveConfiguration();
void _SaveDNSConfiguration();
void _SaveAdaptersConfiguration();
void _ApplyControlsToConfiguration();
status_t _GetPath(const char* name, BPath& path);
status_t _TriggerAutoConfig(const char* device);
bool _ValidateControl(BTextControl* control);
private:
BButton* fApplyButton;
BButton* fRevertButton;
BMenuField* fDeviceMenuField;
BMenuField* fTypeMenuField;
BTextControl* fIPTextControl;
BTextControl* fNetMaskTextControl;
BTextControl* fGatewayTextControl;
BTextControl* fPrimaryDNSTextControl;
BTextControl* fSecondaryDNSTextControl;
BStringView* fErrorMessage;
// TODO: DNS settings do not belong here, do they?
BObjectList<BString> fInterfaces;
Setting* fCurrentSettings;
int32 fStatus;
int fSocket;
};
#endif /* ETHERNET_SETTINGS_VIEW_H */
@@ -0,0 +1,150 @@
/*
* Copyright 2004-2009 Haiku Inc. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Authors:
* Philippe Houdoin
* Fredrik Modéen
*/
#include "InterfaceStatusItem.h"
#include <stdio.h>
#include <stdlib.h>
#include <arpa/inet.h>
#include <net/if.h>
#include <net/if_dl.h>
#include <net/if_media.h>
#include <net/if_types.h>
#include <netinet/in.h>
#include <sys/socket.h>
#include <sys/sockio.h>
#include "NetworkSetupAddOn.h"
#include "Setting.h"
InterfaceStatusItem::InterfaceStatusItem(const char* name, NetworkStatusAddOn* addon)
:
BListItem(0, false),
fIcon(NULL),
fSetting(new Setting(name)),
fAddon(addon)
{
fEnabled = true;
_InitIcon();
}
InterfaceStatusItem::~InterfaceStatusItem()
{
delete fIcon;
}
void InterfaceStatusItem::Update(BView* owner, const BFont* font)
{
BListItem::Update(owner,font);
font_height height;
font->GetHeight(&height);
// TODO: take into account icon height, if he's taller...
SetHeight((height.ascent+height.descent+height.leading) * 3.0 + 8);
}
void
InterfaceStatusItem::DrawItem(BView* owner, BRect /*bounds*/, bool complete)
{
BListView* list = dynamic_cast<BListView*>(owner);
if (!list)
return;
font_height height;
BFont font;
owner->GetFont(&font);
font.GetHeight(&height);
float fntheight = height.ascent+height.descent+height.leading;
BRect bounds = list->ItemFrame(list->IndexOf(this));
rgb_color oldviewcolor = owner->ViewColor();
rgb_color oldlowcolor = owner->LowColor();
rgb_color oldcolor = owner->HighColor();
rgb_color color = oldviewcolor;
if ( IsSelected() )
color = tint_color(color, B_HIGHLIGHT_BACKGROUND_TINT);
owner->SetViewColor( color );
owner->SetHighColor( color );
owner->SetLowColor( color );
owner->FillRect(bounds);
owner->SetViewColor( oldviewcolor);
owner->SetLowColor( oldlowcolor );
owner->SetHighColor( oldcolor );
BPoint iconPt = bounds.LeftTop() + BPoint(4,4);
BPoint namePt = iconPt + BPoint(32+8, fntheight);
BPoint driverPt = iconPt + BPoint(32+8, fntheight*2);
BPoint commentPt = iconPt + BPoint(32+8, fntheight*3);
drawing_mode mode = owner->DrawingMode();
if (fEnabled)
owner->SetDrawingMode(B_OP_OVER);
else {
owner->SetDrawingMode(B_OP_ALPHA);
owner->SetBlendingMode(B_CONSTANT_ALPHA, B_ALPHA_OVERLAY);
owner->SetHighColor(0, 0, 0, 32);
}
owner->DrawBitmapAsync(fIcon, iconPt);
if (!fEnabled)
owner->SetHighColor(tint_color(oldcolor, B_LIGHTEN_2_TINT));
owner->SetFont(be_bold_font);
owner->DrawString(Name(), namePt);
owner->SetFont(be_plain_font);
if (fEnabled) {
BString str("Enabled, IPv4 address: ");
str << fSetting->GetIP();
owner->DrawString(str.String(), driverPt);
if (fSetting->GetAutoConfigure())
owner->DrawString("DHCP enabled", commentPt);
else
owner->DrawString("DHCP Disabled, use static IP adress", commentPt);
} else
owner->DrawString("Disabled.", driverPt);
owner->SetHighColor(oldcolor);
owner->SetDrawingMode(mode);
}
void
InterfaceStatusItem::_InitIcon()
{
BBitmap* icon = NULL;
BResources *resources = fAddon->Resources();
if (resources) {
size_t size;
// printf("Name = %s\n", Name());
// const void *data = resources->LoadResource('ICON', Name(), &size);
// if (!data)
const void *data = resources->LoadResource('ICON', "generic_device", &size);
if (data) {
// Now build the bitmap
icon = new BBitmap(BRect(0, 0, 31, 31), B_CMAP8);
icon->SetBits(data, size, 0, B_CMAP8);
}
}
fIcon = icon;
}
@@ -0,0 +1,48 @@
/*
* Copyright 2004-2009 Haiku Inc. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Authors:
* Philippe Houdoin
* Fredrik Modéen
*/
#ifndef INTERFACESTATUSITEM_H
#define INTERFACESTATUSITEM_H
#include <String.h>
#include <ListItem.h>
#include <Bitmap.h>
#include <net/if.h>
#include <net/if_dl.h>
#include <net/if_media.h>
#include <net/if_types.h>
#include "NetworkStatusAddOn.h"
#include "Setting.h"
class InterfaceStatusItem : public BListItem
{
public:
InterfaceStatusItem(const char* name, NetworkStatusAddOn* addon);
~InterfaceStatusItem();
void DrawItem(BView* owner, BRect bounds, bool complete);
void Update(BView* owner, const BFont* font);
inline const char* Name() { return fSetting->GetName(); }
inline bool Enabled() { return fEnabled; }
inline void SetEnabled(bool enable){ fEnabled = enable; }
inline Setting* GetSetting() { return fSetting; }
private:
void _InitIcon();
bool fEnabled;
BBitmap* fIcon;
Setting* fSetting;
NetworkStatusAddOn* fAddon;
};
#endif /*INTERFACESTATUSITEM_H*/
@@ -0,0 +1,205 @@
/*
* Copyright 2004-2009 Haiku Inc. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Authors:
* Andre Alves Garzia, andre@andregarzia.com
* Stephan Assmuß
* Axel Dörfler
* Philippe Houdoin
* Fredrik Modéen
* Hugo Santos
* Philippe Saint-Pierre
*/
#include "NetworkStatusAddOn.h"
#include <net/if.h>
#include <sys/sockio.h>
#include <stdio.h>
#include <AutoDeleter.h>
#include <ScrollView.h>
#include <Alert.h>
#include "InterfaceStatusItem.h"
#include "NetworkWindow.h"
NetworkSetupAddOn*
get_nth_addon(image_id image, int index)
{
if (index == 0)
return new NetworkStatusAddOn(image);
return NULL;
}
// #pragma mark -
NetworkStatusAddOn::NetworkStatusAddOn(image_id image)
:
NetworkSetupAddOn(image),
BBox(BRect(0, 0, 0, 0), NULL, B_FOLLOW_ALL, B_NAVIGABLE_JUMP, B_NO_BORDER)
{
}
NetworkStatusAddOn::~NetworkStatusAddOn()
{
}
const char*
NetworkStatusAddOn::Name()
{
return "Overview";
}
BView*
NetworkStatusAddOn::CreateView(BRect *bounds)
{
float w, h;
BRect r = *bounds;
#define H_MARGIN 10
#define V_MARGIN 10
#define SMALL_MARGIN 3
if (r.Width() < 100 || r.Height() < 100)
r.Set(0, 0, 100, 100);
ResizeTo(r.Width(), r.Height());
BRect rlv = r;
rlv.bottom -= 72;
rlv.InsetBy(2, 2);
rlv.right -= B_V_SCROLL_BAR_WIDTH;
fListview = new BListView(rlv, NULL, B_SINGLE_SELECTION_LIST,
B_FOLLOW_ALL_SIDES);
fListview->SetSelectionMessage(new BMessage(INTERFACE_SELECTED_MSG));
fListview->SetInvocationMessage(new BMessage(CONFIGURE_INTERFACE_MSG));
AddChild(new BScrollView(NULL, fListview, B_FOLLOW_ALL_SIDES, B_WILL_DRAW
| B_FRAME_EVENTS, false, true));
r.top = r.bottom - 60;
fConfigure = new BButton(r, "configure", "Configure" B_UTF8_ELLIPSIS,
new BMessage(CONFIGURE_INTERFACE_MSG), B_FOLLOW_BOTTOM | B_FOLLOW_LEFT);
fConfigure->GetPreferredSize(&w, &h);
fConfigure->ResizeToPreferred();
fConfigure->SetEnabled(false);
AddChild(fConfigure);
r.left += w + SMALL_MARGIN;
fOnOff = new BButton(r, "onoff", "Disable", new BMessage(ONOFF_INTERFACE_MSG),
B_FOLLOW_BOTTOM | B_FOLLOW_LEFT);
fOnOff->GetPreferredSize(&w, &h);
fOnOff->ResizeToPreferred();
fOnOff->Hide();
AddChild(fOnOff);
fSocket = socket(AF_INET, SOCK_DGRAM, 0);
_LookupDevices();
*bounds = Bounds();
return this;
}
void
NetworkStatusAddOn::AttachedToWindow()
{
fListview->SetTarget(this);
fConfigure->SetTarget(this);
fOnOff->SetTarget(this);
}
void
NetworkStatusAddOn::MessageReceived(BMessage* msg)
{
int nr = fListview->CurrentSelection();
InterfaceStatusItem *item = NULL;
if(nr != -1) {
item = dynamic_cast<InterfaceStatusItem*>(fListview->ItemAt(nr));
}
switch (msg->what) {
case INTERFACE_SELECTED_MSG: {
if (!item)
break;
fConfigure->SetEnabled(item != NULL);
fOnOff->SetEnabled(item != NULL);
if (item == NULL) {
fOnOff->Hide();
break;
}
fOnOff->SetLabel(item->Enabled() ? "Disable" : "Enable");
fOnOff->Show();
break;
}
case CONFIGURE_INTERFACE_MSG: {
if (!item)
break;
NetworkWindow* nw = new NetworkWindow(item->GetSetting());
nw->Show();
break;
}
case ONOFF_INTERFACE_MSG:
if (!item)
break;
item->SetEnabled(!item->Enabled());
fListview->Invalidate();
break;
default:
BBox::MessageReceived(msg);
}
}
status_t
NetworkStatusAddOn::_LookupDevices()
{
// iterate over all interfaces and retrieve minimal status
ifconf config;
config.ifc_len = sizeof(config.ifc_value);
if (ioctl(fSocket, SIOCGIFCOUNT, &config, sizeof(struct ifconf)) < 0)
return B_ERROR;
uint32 count = (uint32)config.ifc_value;
if (count == 0)
return B_ERROR;
void* buffer = malloc(count * sizeof(struct ifreq));
if (buffer == NULL)
return B_ERROR;
MemoryDeleter deleter(buffer);
config.ifc_len = count * sizeof(struct ifreq);
config.ifc_buf = buffer;
if (ioctl(fSocket, SIOCGIFCONF, &config, sizeof(struct ifconf)) < 0)
return B_ERROR;
ifreq* interface = (ifreq*)buffer;
fListview->MakeEmpty();
for (uint32 i = 0; i < count; i++) {
fListview->AddItem(new InterfaceStatusItem(interface->ifr_name, this));
// printf("Name = %s\n", interface->ifr_name);
interface = (ifreq*)((addr_t)interface + IF_NAMESIZE
+ interface->ifr_addr.sa_len);
}
return B_OK;
}
@@ -0,0 +1,47 @@
/*
* Copyright 2004-2009 Haiku Inc. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Authors:
* Philippe Houdoin
* Fredrik Modéen
*/
#ifndef NETWORKSTATUSADDON_H
#define NETWORKSTATUSADDON_H
#include <Box.h>
#include <ListView.h>
#include <Button.h>
#include "NetworkSetupAddOn.h"
class NetworkStatusAddOn : public NetworkSetupAddOn, public BBox
{
public:
NetworkStatusAddOn(image_id addon_image);
~NetworkStatusAddOn();
const char* Name();
BView* CreateView(BRect *bounds);
enum {
INTERFACE_SELECTED_MSG = 'ifce',
CONFIGURE_INTERFACE_MSG = 'conf',
ONOFF_INTERFACE_MSG = 'onof'
};
void AttachedToWindow();
void MessageReceived(BMessage* msg);
private:
status_t _LookupDevices();
BListView* fListview;
BButton* fConfigure;
BButton* fOnOff;
int fSocket;
};
#endif /*NETWORKSTATUSADDON_H*/
@@ -0,0 +1,49 @@
/*
* Copyright 2004-2008 Haiku Inc. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Author:
* Andre Alves Garzia, andre@andregarzia.com
* Fredrik Modéen
*/
#include "NetworkWindow.h"
#include <Application.h>
#include <GroupLayout.h>
#include "EthernetSettingsView.h"
NetworkWindow::NetworkWindow(Setting* setting)
: BWindow(BRect(50, 50, 269, 302), "Network", B_TITLED_WINDOW,
B_NOT_RESIZABLE | B_ASYNCHRONOUS_CONTROLS | B_NOT_ZOOMABLE
| B_AUTO_UPDATE_SIZE_LIMITS)
{
SetLayout(new BGroupLayout(B_HORIZONTAL));
fEthernetView = new EthernetSettingsView(setting);
GetLayout()->AddView(fEthernetView);
}
NetworkWindow::~NetworkWindow()
{
}
void
NetworkWindow::MessageReceived(BMessage* message)
{
switch (message->what) {
default:
BWindow::MessageReceived(message);
}
}
bool
NetworkWindow::QuitRequested()
{
return true;
}
@@ -0,0 +1,29 @@
/*
* Copyright 2004-2008 Haiku Inc. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Author:
* Andre Alves Garzia, andre@andregarzia.com
* Fredrik Modéen
*/
#ifndef NETWORK_WINDOW_H
#define NETWORK_WINDOW_H
#include <Window.h>
#include "EthernetSettingsView.h"
class NetworkWindow : public BWindow {
public:
NetworkWindow(Setting* setting);
virtual ~NetworkWindow();
virtual bool QuitRequested();
virtual void MessageReceived(BMessage* mesage);
private:
EthernetSettingsView* fEthernetView;
};
#endif /* NETWORK_WINDOW_H */
Binary file not shown.
@@ -0,0 +1,195 @@
/*
* Copyright 2004-2007 Haiku Inc. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Author:
* Andre Alves Garzia, andre@andregarzia.com
*/
#include "Setting.h"
#include <String.h>
#include <File.h>
#include <Path.h>
#include <SupportDefs.h>
#include <AutoDeleter.h>
#include <arpa/inet.h>
#include <net/if.h>
#include <net/if_dl.h>
#include <net/if_media.h>
#include <net/if_types.h>
#include <netinet/in.h>
#include <sys/socket.h>
#include <sys/sockio.h>
#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
Setting::Setting(const char *name)
:
fAuto(true)
{
fSocket = socket(AF_INET, SOCK_DGRAM, 0);
fName = name;
ReadConfiguration();
}
Setting::~Setting()
{
close(fSocket);
}
bool
Setting::_PrepareRequest(struct ifreq& request)
{
//This function is used for talking direct to the stack.
//It´s used by _ShowConfiguration.
const char* name = fName.String();
if (strlen(name) > IF_NAMESIZE)
return false;
strcpy(request.ifr_name, name);
return true;
}
void
Setting::ReadConfiguration()
{
ifreq request;
if (!_PrepareRequest(request))
return;
BString text = "dummy";
char address[32];
sockaddr_in* inetAddress = NULL;
// Obtain IP.
if (ioctl(fSocket, SIOCGIFADDR, &request, sizeof(request)) < 0)
return;
inetAddress = (sockaddr_in*)&request.ifr_addr;
if (inet_ntop(AF_INET, &inetAddress->sin_addr, address,
sizeof(address)) == NULL) {
return;
}
fIP = address;
// Obtain netmask.
if (ioctl(fSocket, SIOCGIFNETMASK, &request,
sizeof(request)) < 0) {
return;
}
inetAddress = (sockaddr_in*)&request.ifr_mask;
if (inet_ntop(AF_INET, &inetAddress->sin_addr, address,
sizeof(address)) == NULL) {
return;
}
fNetmask = address;
// Obtain gateway
ifconf config;
config.ifc_len = sizeof(config.ifc_value);
if (ioctl(fSocket, SIOCGRTSIZE, &config, sizeof(struct ifconf)) < 0)
return;
uint32 size = (uint32)config.ifc_value;
if (size == 0)
return;
void *buffer = malloc(size);
if (buffer == NULL)
return;
MemoryDeleter bufferDeleter(buffer);
config.ifc_len = size;
config.ifc_buf = buffer;
if (ioctl(fSocket, SIOCGRTTABLE, &config, sizeof(struct ifconf)) < 0)
return;
ifreq *interface = (ifreq *)buffer;
ifreq *end = (ifreq *)((uint8 *)buffer + size);
while (interface < end) {
route_entry& route = interface->ifr_route;
if (route.flags & RTF_GATEWAY) {
inetAddress = (sockaddr_in*)route.gateway;
fGateway = inet_ntoa(inetAddress->sin_addr);
}
int32 addressSize = 0;
if (route.destination != NULL)
addressSize += route.destination->sa_len;
if (route.mask != NULL)
addressSize += route.mask->sa_len;
if (route.gateway != NULL)
addressSize += route.gateway->sa_len;
interface = (ifreq *)((addr_t)interface +
IF_NAMESIZE + sizeof(route_entry) + addressSize);
}
uint32 flags = 0;
if (ioctl(fSocket, SIOCGIFFLAGS, &request, sizeof(struct ifreq)) == 0)
flags = request.ifr_flags;
fAuto = flags & IFF_AUTO_CONFIGURED;
// read resolv.conf for the dns.
fNameservers.MakeEmpty();
#define MATCH(line, name) \
(!strncmp(line, name, sizeof(name) - 1) && \
(line[sizeof(name) - 1] == ' ' || \
line[sizeof(name) - 1] == '\t'))
register FILE *fp = fopen("/etc/resolv.conf", "r");
if (fp == NULL) {
fprintf(stderr, "failed to open '/etc/resolv.conf' to "
"read nameservers: %s\n", strerror(errno));
return;
}
int nserv = 0;
char buf[1024];
register char *cp; //, **pp;
// register int n;
int MAXNS = 2;
// read the config file
while (fgets(buf, sizeof(buf), fp) != NULL) {
// skip comments
if (*buf == ';' || *buf == '#')
continue;
// read nameservers to query
if (MATCH(buf, "nameserver") && nserv < MAXNS) {
// char sbuf[2];
cp = buf + sizeof("nameserver") - 1;
while (*cp == ' ' || *cp == '\t')
cp++;
cp[strcspn(cp, ";# \t\n")] = '\0';
if ((*cp != '\0') && (*cp != '\n')) {
fNameservers.AddItem(new BString(cp));
nserv++;
}
}
continue;
}
fclose(fp);
}
@@ -0,0 +1,44 @@
/*
* Copyright 2004-2007 Haiku Inc. All rights reserved.
* Distributed under the terms of the MIT License.
*
* Author:
* Andre Alves Garzia, andre@andregarzia.com
*/
#ifndef SETTING_H
#define SETTING_H
#include <ObjectList.h>
#include <String.h>
class Setting {
public:
Setting(const char* name);
virtual ~Setting();
void SetName(BString name);
void SetIP(BString ip) {fIP = ip; }
void SetGateway(BString ip) {fGateway = ip; }
void SetNetmask(BString ip) {fNetmask = ip; }
void SetAutoConfigure(bool t) {fAuto = t; }
const char* GetIP() {return fIP.String(); }
const char* GetGateway() {return fGateway.String(); }
const char* GetNetmask() {return fNetmask.String(); }
const char* GetName() {return fName.String(); }
bool GetAutoConfigure() {return fAuto; }
BObjectList<BString> fNameservers;
void ReadConfiguration();
private:
bool _PrepareRequest(struct ifreq& request);
BString fIP;
BString fGateway;
BString fNetmask;
BString fName;
int fSocket;
bool fAuto;
};
#endif /* SETTINGS_H */
Binary file not shown.

After

Width:  |  Height:  |  Size: 46 KiB

+1
View File
@@ -0,0 +1 @@
/HAIKU_DATA/work/haiku/src/tests/kits/net/preflet/DummyAddOn/Dummy
+1
View File
@@ -0,0 +1 @@
/HAIKU_DATA/work/haiku/src/tests/kits/net/preflet/MultipleAddOns/Multiple
+1
View File
@@ -0,0 +1 @@
../StatusAddOn/Overview
+1
View File
@@ -0,0 +1 @@
../ServicesAddOn/Services
Binary file not shown.

After

Width:  |  Height:  |  Size: 49 KiB