123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107 |
- #include "Session.h"
- #include <limits.h> // for CHAR_BIT
- #include <cstdint> // for uint8_t
- #include <functional> // for __base
- #include <memory> // for shared_ptr, unique_ptr, make_unique
- #include <random> // for default_random_engine, independent_bi...
- #include <type_traits> // for remove_extent_t
- #include <utility> // for move
- #include "ApResolve.h" // for ApResolve, cspot
- #include "AuthChallenges.h" // for AuthChallenges
- #include "BellLogger.h" // for AbstractLogger
- #include "Logger.h" // for CSPOT_LOG
- #include "LoginBlob.h" // for LoginBlob
- #include "Packet.h" // for Packet
- #include "PlainConnection.h" // for PlainConnection, timeoutCallback
- #include "ShannonConnection.h" // for ShannonConnection
- #include "NanoPBHelper.h" // for pbPutString, pbEncode, pbDecode
- #include "pb_decode.h"
- #include "protobuf/authentication.pb.h"
- using random_bytes_engine =
- std::independent_bits_engine<std::default_random_engine, CHAR_BIT, uint8_t>;
- using namespace cspot;
- Session::Session() {
- this->challenges = std::make_unique<cspot::AuthChallenges>();
- }
- Session::~Session() {}
- void Session::connect(std::unique_ptr<cspot::PlainConnection> connection) {
- this->conn = std::move(connection);
- conn->timeoutHandler = [this]() {
- return this->triggerTimeout();
- };
- auto helloPacket = this->conn->sendPrefixPacket(
- {0x00, 0x04}, this->challenges->prepareClientHello());
- auto apResponse = this->conn->recvPacket();
- CSPOT_LOG(info, "Received APHello response");
- auto solvedHello = this->challenges->solveApHello(helloPacket, apResponse);
- conn->sendPrefixPacket({}, solvedHello);
- CSPOT_LOG(debug, "Received shannon keys");
- // Generates the public and priv key
- this->shanConn = std::make_shared<ShannonConnection>();
- // Init shanno-encrypted connection
- this->shanConn->wrapConnection(this->conn, challenges->shanSendKey,
- challenges->shanRecvKey);
- }
- void Session::connectWithRandomAp() {
- auto apResolver = std::make_unique<ApResolve>("");
- auto conn = std::make_unique<cspot::PlainConnection>();
- conn->timeoutHandler = [this]() {
- return this->triggerTimeout();
- };
- auto apAddr = apResolver->fetchFirstApAddress();
- CSPOT_LOG(debug, "Connecting with AP <%s>", apAddr.c_str());
- conn->connect(apAddr);
- this->connect(std::move(conn));
- }
- std::vector<uint8_t> Session::authenticate(std::shared_ptr<LoginBlob> blob) {
- // save auth blob for reconnection purposes
- authBlob = blob;
- // prepare authentication request proto
- auto data = challenges->prepareAuthPacket(blob->authData, blob->authType,
- deviceId, blob->username);
- // Send login request
- this->shanConn->sendPacket(LOGIN_REQUEST_COMMAND, data);
- auto packet = this->shanConn->recvPacket();
- switch (packet.command) {
- case AUTH_SUCCESSFUL_COMMAND: {
- APWelcome welcome;
- CSPOT_LOG(debug, "Authorization successful");
- pbDecode(welcome, APWelcome_fields, packet.data);
- return std::vector<uint8_t>(welcome.reusable_auth_credentials.bytes,
- welcome.reusable_auth_credentials.bytes +
- welcome.reusable_auth_credentials.size);
- break;
- }
- case AUTH_DECLINED_COMMAND: {
- CSPOT_LOG(error, "Authorization declined");
- break;
- }
- default:
- CSPOT_LOG(error, "Unknown auth fail code %d", packet.command);
- }
- return std::vector<uint8_t>(0);
- }
- void Session::close() {
- this->conn->close();
- }
|