#include <KPPPInterface.h>
#include <KPPPUtils.h>
#include <PPPControl.h>
#include "settings_tools.h"
#include <cstring>
KPPPProtocol::KPPPProtocol(const char *name, ppp_phase activationPhase,
uint16 protocolNumber, ppp_level level, int32 addressFamily,
uint32 overhead, KPPPInterface& interface,
driver_parameter *settings, int32 flags,
const char *type, KPPPOptionHandler *optionHandler)
:
KPPPLayer(name, level, overhead),
fActivationPhase(activationPhase),
fProtocolNumber(protocolNumber),
fAddressFamily(addressFamily),
fInterface(interface),
fSettings(settings),
fFlags(flags),
fOptionHandler(optionHandler),
fNextProtocol(NULL),
fEnabled(true),
fUpRequested(true),
fConnectionPhase(PPP_DOWN_PHASE)
{
if (type)
fType = strdup(type);
else
fType = NULL;
const char *sideString = get_parameter_value("side", settings);
if (sideString)
fSide = get_side_string_value(sideString, PPP_LOCAL_SIDE);
else {
if (interface.Mode() == PPP_CLIENT_MODE)
fSide = PPP_LOCAL_SIDE;
else
fSide = PPP_PEER_SIDE;
}
}
KPPPProtocol::~KPPPProtocol()
{
Interface().RemoveProtocol(this);
free(fType);
}
void
KPPPProtocol::Uninit()
{
}
status_t
KPPPProtocol::Control(uint32 op, void *data, size_t length)
{
switch (op) {
case PPPC_GET_PROTOCOL_INFO:
{
if (length < sizeof(ppp_protocol_info_t) || !data)
return B_ERROR;
ppp_protocol_info *info = (ppp_protocol_info*) data;
memset(info, 0, sizeof(ppp_protocol_info_t));
if (Name())
strncpy(info->name, Name(), PPP_HANDLER_NAME_LENGTH_LIMIT);
if (Type())
strncpy(info->type, Type(), PPP_HANDLER_NAME_LENGTH_LIMIT);
info->activationPhase = ActivationPhase();
info->addressFamily = AddressFamily();
info->flags = Flags();
info->side = Side();
info->level = Level();
info->overhead = Overhead();
info->connectionPhase = fConnectionPhase;
info->protocolNumber = ProtocolNumber();
info->isEnabled = IsEnabled();
info->isUpRequested = IsUpRequested();
break;
}
case PPPC_ENABLE:
if (length < sizeof(uint32) || !data)
return B_ERROR;
SetEnabled(*((uint32*)data));
break;
default:
return B_BAD_VALUE;
}
return B_OK;
}
status_t
KPPPProtocol::StackControl(uint32 op, void *data)
{
switch (op) {
default:
return B_BAD_VALUE;
}
return B_OK;
}
void
KPPPProtocol::SetEnabled(bool enabled)
{
fEnabled = enabled;
if (!enabled) {
if (IsUp() || IsGoingUp())
Down();
} else if (!IsUp() && !IsGoingUp() && IsUpRequested() && Interface().IsUp())
Up();
}
bool
KPPPProtocol::IsAllowedToSend() const
{
return IsEnabled() && IsUp() && IsProtocolAllowed(*this);
}
void
KPPPProtocol::UpStarted()
{
fConnectionPhase = PPP_ESTABLISHMENT_PHASE;
}
void
KPPPProtocol::DownStarted()
{
fConnectionPhase = PPP_TERMINATION_PHASE;
}
void
KPPPProtocol::UpFailedEvent()
{
fConnectionPhase = PPP_DOWN_PHASE;
Interface().StateMachine().UpFailedEvent(this);
}
void
KPPPProtocol::UpEvent()
{
fConnectionPhase = PPP_ESTABLISHED_PHASE;
Interface().StateMachine().UpEvent(this);
}
void
KPPPProtocol::DownEvent()
{
fConnectionPhase = PPP_DOWN_PHASE;
Interface().StateMachine().DownEvent(this);
}