#include <QColor>
#include <QCryptographicHash>
#include <QPushButton>
+#include <QPointer>
+#include <QSettings>
+
+#include "hmac.h"
//enable linux to read /dev/random
#ifdef __linux__
//amount of random bits needed:
#define RANDNEED 160
+static QPointer<EFilter>efilter;
+
MKeyGen::MKeyGen()
{
setWindowTitle(tr("Magic Smoke Key Generator"));
//pre-init random buffer
randstat=-1;
- randent=0;
+ connect(efilter,SIGNAL(moreBits()),this,SLOT(updateProps()));
//make sure all mouse events arrive
setMouseTracking(true);
QVBoxLayout*vl;
lab->setWordWrap(true);
lab->setMouseTracking(true);
//buffer display
- vl->addWidget(randlab=new QLabel(tr("Current random buffer: %1 Bits").arg(randent)),0);
+ vl->addWidget(randlab=new QLabel(tr("Current random buffer: %1 Bits").arg(efilter->entropy())),0);
randlab->setMouseTracking(true);
randlab->setFrameShape(QFrame::Box);
randlab->setAutoFillBackground(true);
hl->addWidget(ccbtn=new QPushButton(tr("&Cancel")),0);
connect(ccbtn,SIGNAL(clicked()),this,SLOT(reject()));
+ //make sure widgets look right
+ updateProps();
+
+ //make window really big
+ showMaximized();
+}
+
+MKeyGen::~MKeyGen()
+{
+}
+
+void MKeyGen::updateProps()
+{
+ randlab->setText(tr("Current random buffer: %1 Bits").arg(efilter->entropy()));
+ if(efilter->entropy()<RANDNEED){
+ //check whether we need to set it
+ if(randstat==0)return;
+ randstat=0;
+ //set label color
+ QPalette pal=randlab->palette();
+ pal.setColor(QPalette::Window,QColor("#ff8080"));
+ randlab->setPalette(pal);
+ //set button
+ okbtn->setEnabled(false);
+ }else{
+ //check whether we need to set it
+ if(randstat==1)return;
+ randstat=1;
+ //set label color
+ QPalette pal=randlab->palette();
+ pal.setColor(QPalette::Window,QColor("#80ff80"));
+ randlab->setPalette(pal);
+ //set button
+ okbtn->setEnabled(true);
+ }
+}
+
+QString MKeyGen::getKey()
+{
+ if(efilter->entropy()<RANDNEED)return "";
+ return efilter->getRandom(40).toHex();
+}
+
+
+EFilter::EFilter()
+{
+ efilter=this;
+ randctr=0;
+ //preload seed
+ QSettings set;
+ randbuf.append(set.value("randomseed").toByteArray());
+ randent=randbuf.size();
+ if(randent>=RANDNEED)set.setValue("randomseed",getRandom(RANDNEED));
//if Linux: try to pre-load some random
#ifdef __linux__
int fd=::open("/dev/random",O_RDONLY|O_NONBLOCK);
int rd=::read(fd,buf,sizeof(buf));
if(rd>0){
randbuf.append(QByteArray(buf,rd));
- randent=rd*8;
+ randent+=rd*8;
}
::close(fd);
}
#endif
+}
- //make sure widgets look right
- updateProps();
-
- //make window really big
- showMaximized();
+EFilter::~EFilter()
+{
+ QSettings set;
+ set.setValue("randomseed",getRandom(RANDNEED));
+}
+
+EFilter* EFilter::instance()
+{
+ return efilter;
+}
+
+QByteArray EFilter::getRandom(int bytes)
+{
+ QByteArray ret;
+ while(ret.size()<bytes){
+ randlast.append(QByteArray::number(randctr));
+ randlast=SMHmac::hmac(randlast,randbuf,QCryptographicHash::Sha1);
+ randctr++;
+ randent--;
+ ret.append(randlast);
+ }
+ if(randent<0)randent=0;
+ return ret.left(bytes);
+}
+
+int EFilter::entropy()
+{
+ return randent;
}
-MKeyGen::~MKeyGen(){}
-bool MKeyGen::event(QEvent*e)
+
+bool EFilter::eventFilter(QObject*,QEvent*e)
{
//add to random buffer for key and mouse events
switch(e->type()){
//ignore
break;
}
- return QDialog::event(e);
+ return false;
}
-void MKeyGen::addBit(int b)
+void EFilter::addBit(int b)
{
//add bit to buffer
randbuf.append((b>>24)&0xff);
randbuf.append(t&0xff);
randent++;
}
- //update display
- updateProps();
- randlab->setText(tr("Current random buffer: %1 Bits").arg(randent));
-}
-
-void MKeyGen::updateProps()
-{
- if(randent<RANDNEED){
- //check whether we need to set it
- if(randstat==0)return;
- randstat=0;
- //set label color
- QPalette pal=randlab->palette();
- pal.setColor(QPalette::Window,QColor("#ff8080"));
- randlab->setPalette(pal);
- //set button
- okbtn->setEnabled(false);
- }else{
- //check whether we need to set it
- if(randstat==1)return;
- randstat=1;
- //set label color
- QPalette pal=randlab->palette();
- pal.setColor(QPalette::Window,QColor("#80ff80"));
- randlab->setPalette(pal);
- //set button
- okbtn->setEnabled(true);
+ //pack buffer if necessary (>10kB)
+ if(randbuf.size()>=10240){
+ randbuf=getRandom(80);
+ if(randent>320)randent=320;
}
+ //update display
+ emit moreBits();
}
-QString MKeyGen::getKey()
-{
- if(randent<RANDNEED)return "";
- return QCryptographicHash::hash(randbuf,QCryptographicHash::Sha1).toHex();
-}
-
-
-bool EFilter::eventFilter(QObject*,QEvent*e)
+QByteArray getRandom(int num)
{
- if(e->type()==QEvent::KeyPress)
- qDebug("key");
- return false;
+ if(efilter.isNull())return QByteArray();
+ return efilter->getRandom(num);
}
QString getKey();
- protected:
- bool event(QEvent*);
private:
- QByteArray randbuf;
- int randent;
QLabel*randlab;
int randstat;
QPushButton *okbtn,*ccbtn;
- void addBit(int);
+ private slots:
void updateProps();
};
class EFilter:public QObject
{
Q_OBJECT
+ public:
+ EFilter();
+ ~EFilter();
+
+ static EFilter*instance();
+
+ int entropy();
+ QByteArray getRandom(int);
+ signals:
+ void moreBits();
protected:
bool eventFilter(QObject*,QEvent*);
+ private:
+ QByteArray randbuf,randlast;
+ int randent,randctr;
+ void addBit(int);
};
+//shortcut:
+QByteArray getRandom(int);
+
#endif
#include <QLocale>
#include <QInputDialog>
#include <QMessageBox>
+#include <QHostInfo>
+#include <QDir>
#include "keygen.h"
#include "mainwindow.h"
int main(int argc,char**argv)
{
+ //create global app
QApplication app(argc,argv);
- EFilter ef;
- app.installEventFilter(&ef);
-
+ //locate settings
app.setOrganizationName("MagicSmoke");
app.setApplicationName("MagicSmoke");
- //try to find appropriate locale
- QString lang=QSettings().value("lang","C").toString();
- if(lang=="C")lang=QLocale::system().name();
+ //install event filter for random generator
+ EFilter ef;
+ app.installEventFilter(&ef);
+ //try to find appropriate locale
+ QString lang=QSettings().value("lang","--").toString();
+ if(lang=="--"){
+ lang=QLocale::system().name();
+ int cur=0;
+ QStringList langs;
+ langs<<"C - default";
+ QStringList files=QDir(app.applicationDirPath()).entryList(QStringList()<<"smoke_*.qm", QDir::Files, QDir::Name);
+ for(int i=0;i<files.size();i++){
+ QString l=files[i].mid(6);
+ l.chop(3);
+ langs<<l;
+ if(l==lang)cur=langs.size()-1;
+ }
+ bool ok;
+ QString lc;
+ lc=QInputDialog::getItem(0,"Chose Language","Language:",langs,cur,false,&ok);
+ if(&ok){
+ lang=lc.split(' ').at(0);
+ QSettings().setValue("lang",lang);
+ }
+ }
qDebug("Loading language %s",lang.toAscii().data());
QTranslator qttrans;
qttrans.load("qt_"+lang);
mstrans.load("smoke_"+lang);
app.installTranslator(&mstrans);
+ //check/generate host settings
if(!QSettings().contains("hostkey")){
MKeyGen mkg;
if(mkg.exec()==QDialog::Accepted)
return 1;
}
}
+ if(!QSettings().contains("hostname")){
+ bool ok;
+ QString hn=QInputDialog::getText(0,app.translate("initkey","Enter Host Name"),
+ app.translate("initkey","Host name:"),QLineEdit::Normal,QHostInfo::localHostName(),
+ &ok);
+ if(ok && !hn.isEmpty())
+ QSettings().setValue("hostname",hn);
+ else{
+ QMessageBox::critical(0,app.translate("initkey","Warning"), app.translate("initkey","Magic Smoke needs a host name. You have to configure one before you can use the program."));
+ return 1;
+ }
+ }
+ //check/generate profile
QString iprof;
if(!QSettings().childGroups().contains("profiles")){
iprof="0";
QSettings().setValue("profiles/0/name",ipname);
}
+ //open main window
MMainWindow mmw;
- mmw.show();
+ mmw.showMaximized();
return app.exec();
}
//
#include "mainwindow.h"
+#include "keygen.h"
#include <QHttp>
#include <QFile>
#include <QByteArray>
#include <QMenuBar>
#include <QMenu>
+#include <QStackedWidget>
+#include <QGridLayout>
+#include <QLabel>
+#include <QComboBox>
+#include <QCheckBox>
+#include <QLineEdit>
+#include <QHBoxLayout>
+#include <QSpinBox>
+#include <QPushButton>
+#include <QSettings>
+#include <QInputDialog>
MMainWindow::MMainWindow()
{
+ setWindowTitle("Magic Smoke");
+ //create Menu Bar
QMenuBar*mb=menuBar();
QMenu*m=mb->addMenu("&File");
m->addAction("&Test",this,SLOT(testrequest()));
m->addSeparator();
m->addAction("&Close Session",this,SLOT(close()));
+
+ //create central stack
+ setCentralWidget(main=new QStackedWidget);
+
+ //create login widget
+ main->addWidget(loginwidget=new QWidget);
+ QGridLayout*gl;
+ loginwidget->setLayout(gl=new QGridLayout);
+ QLabel*lab;
+ int lctr=0;
+ gl->addWidget(lab=new QLabel(tr("Profile:")),lctr,0);
+ lab->setAlignment(Qt::AlignRight);
+ gl->addWidget(profiles=new QComboBox,lctr,1);
+ connect(profiles,SIGNAL(currentIndexChanged(int)),this,SLOT(loadProfile()));
+ gl->addWidget(usealterhost=new QCheckBox(tr("Alternate Hostname:")),++lctr,0);
+ gl->addWidget(alterhostname=new QLineEdit,lctr,1);
+ connect(usealterhost,SIGNAL(toggled(bool)),alterhostname,SLOT(setEnabled(bool)));
+ gl->addWidget(lab=new QLabel(tr("Server URL:")),++lctr,0);
+ lab->setAlignment(Qt::AlignRight);
+ gl->addWidget(serverurl=new QLineEdit,lctr,1);
+ gl->addWidget(useproxy=new QCheckBox(tr("Proxy:")),++lctr,0);
+ QHBoxLayout*hl;
+ gl->addLayout(hl=new QHBoxLayout,lctr,1);
+ hl->addWidget(proxyname=new QLineEdit,1);
+ hl->addWidget(new QLabel(":"),0);
+ hl->addWidget(proxyport=new QSpinBox,0);
+ proxyport->setRange(1,65535);
+ connect(useproxy,SIGNAL(toggled(bool)),proxyname,SLOT(setEnabled(bool)));
+ connect(useproxy,SIGNAL(toggled(bool)),proxyport,SLOT(setEnabled(bool)));
+ QFrame*frm;
+ gl->addWidget(frm=new QFrame,++lctr,0,1,2);
+ frm->setFrameShape(QFrame::HLine);
+ gl->addWidget(lab=new QLabel(tr("Username:")),++lctr,0);
+ lab->setAlignment(Qt::AlignRight);
+ gl->addWidget(username=new QLineEdit,lctr,1);
+ gl->addWidget(lab=new QLabel(tr("Password:")),++lctr,0);
+ lab->setAlignment(Qt::AlignRight);
+ gl->addWidget(password=new QLineEdit,lctr,1);
+ password->setEchoMode(QLineEdit::Password);
+ gl->setRowStretch(++lctr,10);
+ gl->addLayout(hl=new QHBoxLayout,++lctr,0,1,2);
+ QPushButton*p;
+ hl->addWidget(p=new QPushButton("new Profile"),0);
+ connect(p,SIGNAL(clicked()),this,SLOT(newProfile()));
+ hl->addStretch(10);
+ hl->addWidget(p=new QPushButton("Login"),0);
+ connect(p,SIGNAL(clicked()),this,SLOT(saveProfile()));
+ connect(p,SIGNAL(clicked()),this,SLOT(startLogin()));
+ hl->addWidget(p=new QPushButton("Exit"),0);
+ connect(p,SIGNAL(clicked()),this,SLOT(close()));
+ initProfiles();
+ loadProfile();
+
+ //make login the default
+ mb->setEnabled(false);
+ main->setCurrentWidget(loginwidget);
}
-void MMainWindow::testrequest()
+void MMainWindow::initProfiles()
+{
+ QSettings set;
+ set.beginGroup("profiles");
+ QStringList prf=set.childGroups();
+ profiles->clear();
+ for(int i=0;i<prf.size();i++){
+ profiles->addItem(set.value(prf[i]+"/name").toString(),prf[i]);
+ }
+}
+
+void MMainWindow::loadProfile()
+{
+ QString key=profiles->itemData(profiles->currentIndex()).toString();
+ QSettings set;
+ set.beginGroup("profiles/"+key);
+ usealterhost->setChecked(set.value("usealternatehost",false).toBool());
+ alterhostname->setText(set.value("alternatehostname").toString());
+ alterhostname->setEnabled(usealterhost->isChecked());
+ serverurl->setText(set.value("serverurl","http://my.host.com/path/machine.php").toString());
+ useproxy->setChecked(set.value("useproxy",false).toBool());
+ proxyname->setText(set.value("proxyname","proxy").toString());
+ proxyport->setValue(set.value("proxyport",74).toInt());
+ proxyname->setEnabled(useproxy->isChecked());
+ proxyport->setEnabled(useproxy->isChecked());
+ username->setText(set.value("username").toString());
+ password->setText("");
+}
+
+void MMainWindow::saveProfile()
+{
+ QString key=profiles->itemData(profiles->currentIndex()).toString();
+ QSettings set;
+ set.beginGroup("profiles/"+key);
+ set.setValue("usealternatehost",usealterhost->isChecked());
+ set.setValue("alternatehostname",alterhostname->text());
+ set.setValue("serverurl",serverurl->text());
+ set.setValue("useproxy",useproxy->isChecked());
+ set.setValue("proxyname",proxyname->text());
+ set.setValue("proxyport",proxyport->value());
+ set.setValue("username",username->text());
+}
+
+void MMainWindow::newProfile()
+{
+ //scan for existing ones...
+ QSettings set;
+ set.beginGroup("profiles");
+ QStringList prf=set.childGroups();
+ QStringList prn;
+ for(int i=0;i<prf.size();i++){
+ prn<<set.value(prf[i]+"/name").toString();
+ }
+ //create new index
+ QString pidx;
+ for(int i=0;;i++){
+ pidx=QString::number(i);
+ if(!prf.contains(pidx))break;
+ }
+ //request name
+ QString pname;
+ while(1){
+ bool ok;
+ pname=QInputDialog::getText(this,tr("New Profile"),tr("Please enter a profile name. It must be non-empty and must not be used yet:"),QLineEdit::Normal,pname,&ok);
+ if(!ok)return;
+ if(pname.isEmpty())continue;
+ if(!prn.contains(pname))break;
+ }
+ //create
+ set.setValue(pidx+"/name",pname);
+ profiles->addItem(pname,pidx);
+ profiles->setCurrentIndex(profiles->count()-1);
+}
+
+void MMainWindow::startLogin()
+{
+ //make it impossible for the user to interfere
+ setEnabled(false);
+ //start request
+ startRequest("startsession",getRandom(32).toHex(),SLOT(loginStage2(int,bool)));
+}
+
+void MMainWindow::startRequest(QString hreq,QByteArray data,char*myslot)
{
req=new QHttp("localhost");
- connect(req,SIGNAL(requestFinished(int,bool)),this,SLOT(trfin(int,bool)));
+ connect(req,SIGNAL(requestFinished(int,bool)),this,myslot);
QHttpRequestHeader hrh("POST","/~konrad/smoke/machine.php");
hrh.setValue("Host","localhost");
- hrh.setValue("X-MagicSmoke-Request","testdueluEhue");
- QByteArray tdata("blah\nschwafel\r\nseier");
- hrh.setContentLength(tdata.size());
- hrh.setContentType("text/x-magicsmoke");
+ hrh.setValue("X-MagicSmoke-Request",hreq);
+ hrh.setValue("X-MagicSmoke-Session",sessionid);
+ hrh.setContentLength(data.size());
+ hrh.setContentType("application/x-magicsmoke");
qDebug("Requesting data with:\n%s",hrh.toString().toAscii().data());
- req->request(hrh,tdata);
+ req->request(hrh,data);
}
-void MMainWindow::trfin(int id,bool err)
+void MMainWindow::loginStage2(int id,bool err)
{
qDebug("Received Request finish for ID=%i Status=%s",id,err?"Error":"Ok");
if(err){
QHttpResponseHeader hrh=req->lastResponse();
QByteArray data=req->readAll();
qDebug("HTTP Response Headers:\n%s",hrh.toString().toAscii().data());
- QFile fd("rsp"+QString::number(id)+".html");
- fd.open(QIODevice::WriteOnly);
- fd.write(data);
- fd.close();
+ qDebug("HTTP Response Body:\n%s\n<-->",data.data());
}
+ req->disconnect();
+ req->deleteLater();
+ setEnabled(true);
}
#define MAGICSMOKE_MAINWINDOW_H
#include <QMainWindow>
+#include <QDialog>
+#include <QPointer>
class QHttp;
+class QStackedWidget;
+class QComboBox;
+class QLineEdit;
+class QCheckBox;
+class QSpinBox;
class MMainWindow:public QMainWindow
{
Q_OBJECT
public:
MMainWindow();
- public slots:
- void testrequest();
- void trfin(int,bool);
private:
QHttp*req;
+ QString sessionid;
+ QStackedWidget*main;
+ QWidget*loginwidget;
+ QCheckBox*usealterhost,*useproxy;
+ QLineEdit*alterhostname,*serverurl,*proxyname,*username,*password;
+ QSpinBox*proxyport;
+ QComboBox*profiles;
+
+ private slots:
+ //handling of login/profile screen
+ void initProfiles();
+ void loadProfile();
+ void saveProfile();
+ void newProfile();
+ void startLogin();
+ void loginStage2(int,bool);
+
+ //request handling
+ void startRequest(QString,QByteArray,char*);
};
#endif
TARGET = msmoke
#build for debug or release?
-CONFIG += release
-#CONFIG += debug
+#CONFIG += release
+CONFIG += debug
CONFIG += qt thread
QT += xml network
<context>
<name>MKeyGen</name>
<message>
- <location filename="keygen.cpp" line="132"/>
+ <location filename="keygen.cpp" line="86"/>
<source>Current random buffer: %1 Bits</source>
<translation>Aktueller Zufallspuffer: %1 Bits</translation>
</message>
<message>
- <location filename="keygen.cpp" line="36"/>
+ <location filename="keygen.cpp" line="42"/>
<source>Magic Smoke Key Generator</source>
<translation>Magic Smoke Schlüsselgenerator</translation>
</message>
<message>
- <location filename="keygen.cpp" line="47"/>
+ <location filename="keygen.cpp" line="53"/>
<source><html><h1>Key Generation</h1>
I am currently collecting random bits in order to generate a host key for this installation. Please use mouse and keyboard to generate more random. Alternatively you can load a key from an external medium.<p>
At least %1 Bits of random are required.</source>
<translation><html><h1>Schlüsselgenerierung</h1>Das Programm sammelt gerade Zufallsbits für diese Installation. Bitte benutzen Sie Maus und Tastatur, um mehr Zufall zu generieren. Alternativ können Sie auch einen fertigen Schlüssel von einem externen Medium laden.<p>Mindestens %1 Zufallsbits werden gebraucht.</translation>
</message>
<message>
- <location filename="keygen.cpp" line="62"/>
+ <location filename="keygen.cpp" line="68"/>
<source>&OK</source>
<translation>&Ok</translation>
</message>
<message>
- <location filename="keygen.cpp" line="64"/>
+ <location filename="keygen.cpp" line="70"/>
<source>&Cancel</source>
<translation>&Abbrechen</translation>
</message>
</context>
<context>
+ <name>MMainWindow</name>
+ <message>
+ <location filename="mainwindow.cpp" line="51"/>
+ <source>Profile:</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="55"/>
+ <source>Alternate Hostname:</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="58"/>
+ <source>Server URL:</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="61"/>
+ <source>Proxy:</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="73"/>
+ <source>Username:</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="76"/>
+ <source>Password:</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="161"/>
+ <source>New Profile</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="161"/>
+ <source>Please enter a profile name. It must be non-empty and must not be used yet:</source>
+ <translation type="unfinished"></translation>
+ </message>
+</context>
+<context>
<name>initkey</name>
<message>
- <location filename="main.cpp" line="47"/>
+ <location filename="main.cpp" line="87"/>
<source>Warning</source>
<translation type="unfinished"></translation>
</message>
<message>
- <location filename="main.cpp" line="47"/>
+ <location filename="main.cpp" line="75"/>
<source>Magic Smoke needs a host key. You have to generate one before you can use the program.</source>
<translation type="unfinished"></translation>
</message>
+ <message>
+ <location filename="main.cpp" line="81"/>
+ <source>Enter Host Name</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="main.cpp" line="82"/>
+ <source>Host name:</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="main.cpp" line="87"/>
+ <source>Magic Smoke needs a host name. You have to configure one before you can use the program.</source>
+ <translation type="unfinished"></translation>
+ </message>
</context>
<context>
<name>initprofile</name>
<message>
- <location filename="main.cpp" line="55"/>
+ <location filename="main.cpp" line="96"/>
<source>default</source>
<comment>initial profile</comment>
<translation type="unfinished"></translation>
</message>
<message>
- <location filename="main.cpp" line="56"/>
+ <location filename="main.cpp" line="97"/>
<source>Create Initial Profile</source>
<translation type="unfinished"></translation>
</message>
<message>
- <location filename="main.cpp" line="56"/>
+ <location filename="main.cpp" line="97"/>
<source>You need a profile to work with Magic Smoke. Magic Smoke will now create one for you. Please enter the name you wish to give this profile.</source>
<translation type="unfinished"></translation>
</message>
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE TS><TS version="1.1" language="de">
-<defaultcodec></defaultcodec>
<context>
<name>MKeyGen</name>
<message>
- <location filename="keygen.cpp" line="132"/>
+ <location filename="keygen.cpp" line="86"/>
<source>Current random buffer: %1 Bits</source>
<translation>Aktueller Füllschdand vom dem Zufallsbuffer: %1 Bids</translation>
</message>
<message>
- <location filename="keygen.cpp" line="36"/>
+ <location filename="keygen.cpp" line="42"/>
<source>Magic Smoke Key Generator</source>
<translation>Mädschig Schmohg Schlüsselgenerador</translation>
</message>
<message>
- <location filename="keygen.cpp" line="47"/>
+ <location filename="keygen.cpp" line="53"/>
<source><html><h1>Key Generation</h1>
I am currently collecting random bits in order to generate a host key for this installation. Please use mouse and keyboard to generate more random. Alternatively you can load a key from an external medium.<p>
At least %1 Bits of random are required.</source>
<translation><html><h1>Schlüsselgenerierung</h1>Das Brogramm sammeld grade Zufallsbids für diese Inschdalladsion. <br>Das iss im Grunde ne' ganz eefache Sache. Basse off: Du waggelsd ä bissl an dor Maus und hämmerst wie ä Beglobbder off de Dasdadur. Dann wenn's Brogramm genug Zufall had wird de rode Leisde unden grün. Das heesd Du gannst offhörn und Disch wiedor wie'n normaler Mensch benehm'.Wenn Dir das nich bassd gannsde och jemand andres den Schrodd machn' lassn' und 'ne Schlüsseldadei laden.<p>Mindeschdens %1 Zufallsbids brauchsde. Geene Sorsche das gehd fix.</translation>
</message>
<message>
- <location filename="keygen.cpp" line="62"/>
+ <location filename="keygen.cpp" line="68"/>
<source>&OK</source>
<translation>Nu &glar! Nehm'sch.</translation>
</message>
<message>
- <location filename="keygen.cpp" line="64"/>
+ <location filename="keygen.cpp" line="70"/>
<source>&Cancel</source>
<translation>&Nee lass mal.</translation>
</message>
</context>
<context>
+ <name>MMainWindow</name>
+ <message>
+ <location filename="mainwindow.cpp" line="51"/>
+ <source>Profile:</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="55"/>
+ <source>Alternate Hostname:</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="58"/>
+ <source>Server URL:</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="61"/>
+ <source>Proxy:</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="73"/>
+ <source>Username:</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="76"/>
+ <source>Password:</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="161"/>
+ <source>New Profile</source>
+ <translation type="unfinished"></translation>
+ </message>
+ <message>
+ <location filename="mainwindow.cpp" line="161"/>
+ <source>Please enter a profile name. It must be non-empty and must not be used yet:</source>
+ <translation type="unfinished"></translation>
+ </message>
+</context>
+<context>
<name>initkey</name>
<message>
- <location filename="main.cpp" line="47"/>
+ <location filename="main.cpp" line="87"/>
<source>Warning</source>
<translation>Dumm gelaufen</translation>
</message>
<message>
- <location filename="main.cpp" line="47"/>
+ <location filename="main.cpp" line="75"/>
<source>Magic Smoke needs a host key. You have to generate one before you can use the program.</source>
<translation>Mädschig Schmohg brauchd 'nen Schlüssel. Desweschen isser beleidschd. Beim nächsden Schdard mussde ihn einen mach'n lass'n.</translation>
</message>
+ <message>
+ <location filename="main.cpp" line="81"/>
+ <source>Enter Host Name</source>
+ <translation>Gombjudername eingäbn</translation>
+ </message>
+ <message>
+ <location filename="main.cpp" line="82"/>
+ <source>Host name:</source>
+ <translation>Gombjudername:</translation>
+ </message>
+ <message>
+ <location filename="main.cpp" line="87"/>
+ <source>Magic Smoke needs a host name. You have to configure one before you can use the program.</source>
+ <translation>Mädschig Schmohg brauchd 'nen Namen für diesen Gombjuder. Desweschen isser beleidschd. Beim nächsden Schdard mussde ihn eingäben. </translation>
+ </message>
</context>
<context>
<name>initprofile</name>
<message>
- <location filename="main.cpp" line="55"/>
+ <location filename="main.cpp" line="96"/>
<source>default</source>
<comment>initial profile</comment>
- <translation>Schandardbrofiel</translation>
+ <translation>Schdandardbrofiel</translation>
</message>
<message>
- <location filename="main.cpp" line="56"/>
+ <location filename="main.cpp" line="97"/>
<source>Create Initial Profile</source>
<translation>Erschdes Brofiel anlechen</translation>
</message>
<message>
- <location filename="main.cpp" line="56"/>
+ <location filename="main.cpp" line="97"/>
<source>You need a profile to work with Magic Smoke. Magic Smoke will now create one for you. Please enter the name you wish to give this profile.</source>
<translation>Gugge, Du brauchsd sowas wie'n Brofiel. Mädschig Schmohg iss nedd und machd eens für Disch. Desderweschen brauchsde jedsd nur noch n Namen dafür eindibben.</translation>
</message>
);
$SMOKEREQUEST=strtolower($_SERVER["HTTP_X_MAGICSMOKE_REQUEST"]);
if(!in_array($SMOKEREQUEST,$ALLOWEDREQUESTS)){
- header("X-MagicSmoke-Status","InvalidRequest");
+ header("X-MagicSmoke-Status: InvalidRequest");
exit();
}
$REQUESTDATA="";
// server info can be answered without performing any more initialization
if($SMOKEREQUEST=="serverinfo"){
- header("X-MagicSmoke-Status","Ok");
+ header("X-MagicSmoke-Status: Ok");
print("<Info>\n <ServerVersion proto=\"0000 0000\">$MAGICSMOKEVERSION</ServerVersion\n <AuthAlgorithm>$ClientAuthAlgo</AuthAlgorithm>\n</Info>");
exit();
}
// request to start a session
if($SMOKEREQUEST=="startsession"){
//TODO: start session
+ echo "blah session";
exit();
}
//request to close a session
if($SMOKEREQUEST=="closesession"){
//TODO: close session
- header("X-MagicSmoke-Status","Ok");
+ header("X-MagicSmoke-Status: Ok");
exit();
}
//request session authentication
-
+//EOF
+die("Internal Error");
?>
\ No newline at end of file