Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Op25 update Nov 2023 #883

Merged
merged 3 commits into from
Dec 2, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion lib/op25_repeater/lib/dmr_slot.h
Original file line number Diff line number Diff line change
Expand Up @@ -104,7 +104,7 @@ class dmr_slot {
int d_slot_mask;
int d_src_id;
bool d_terminated;
log_ts logts;
log_ts& logts;
CBPTC19696 bptc;
CDMRTrellis trellis;
ezpwd::RS<255,252> rs12; // Reed-Solomon(12,9) object for Link Control decode
Expand Down
37 changes: 23 additions & 14 deletions lib/op25_repeater/lib/p25_crypt_algs.cc
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ p25_crypt_algs::p25_crypt_algs(log_ts& logger, int debug, int msgq_id) :
logts(logger),
d_debug(debug),
d_msgq_id(msgq_id),
d_fr_type(FT_UNK),
d_pr_type(PT_UNK),
d_algid(0x80),
d_keyid(0),
d_mi{0},
Expand All @@ -59,7 +59,7 @@ void p25_crypt_algs::key(uint16_t keyid, uint8_t algid, const std::vector<uint8_
}

// generic entry point to prepare for decryption
bool p25_crypt_algs::prepare(uint8_t algid, uint16_t keyid, frame_type fr_type, uint8_t *MI) {
bool p25_crypt_algs::prepare(uint8_t algid, uint16_t keyid, protocol_type pr_type, uint8_t *MI) {
bool rc = false;
d_algid = algid;
d_keyid = keyid;
Expand All @@ -79,7 +79,7 @@ bool p25_crypt_algs::prepare(uint8_t algid, uint16_t keyid, frame_type fr_type,
switch (algid) {
case 0xaa: // ADP RC4
d_adp_position = 0;
d_fr_type = fr_type;
d_pr_type = pr_type;
adp_keystream_gen();
rc = true;
break;
Expand All @@ -91,15 +91,15 @@ bool p25_crypt_algs::prepare(uint8_t algid, uint16_t keyid, frame_type fr_type,
}

// generic entry point to perform decryption
bool p25_crypt_algs::process(packed_codeword& PCW) {
bool p25_crypt_algs::process(packed_codeword& PCW, frame_type fr_type, int voice_subframe) {
bool rc = false;

if (d_key_iter == d_keys.end())
return false;

switch (d_algid) {
case 0xaa: // ADP RC4
rc = adp_process(PCW);
rc = adp_process(PCW, fr_type, voice_subframe);
break;

default:
Expand All @@ -110,39 +110,48 @@ bool p25_crypt_algs::process(packed_codeword& PCW) {
}

// ADP RC4 decryption
bool p25_crypt_algs::adp_process(packed_codeword& PCW) {
bool p25_crypt_algs::adp_process(packed_codeword& PCW, frame_type fr_type, int voice_subframe) {
bool rc = true;
size_t offset = 0;
size_t offset = 256;

if (d_key_iter == d_keys.end())
return false;

switch (d_fr_type) {
switch (fr_type) {
case FT_LDU1:
offset = 0;
break;
case FT_LDU2:
offset = 101;
break;
case FT_4V_0:
offset += 7 * voice_subframe;
break;
case FT_4V_1:
offset += 7 * (voice_subframe + 4);
break;
case FT_4V_2:
offset += 7 * (voice_subframe + 8);
break;
case FT_4V_3:
offset += 7 * (voice_subframe + 12);
break;
case FT_2V:
case FT_4V:
offset = 0;
offset += 7 * (voice_subframe + 16);
break;
default:
rc = false;
break;
}
if ((d_fr_type == FT_LDU1) || (d_fr_type == FT_LDU2)) {
if (d_pr_type == PT_P25_PHASE1) {
//FDMA
offset += (d_adp_position * 11) + 267 + ((d_adp_position < 8) ? 0 : 2); // voice only; skip LCW and LSD
d_adp_position = (d_adp_position + 1) % 9;
for (int j = 0; j < 11; ++j) {
PCW[j] = adp_keystream[j + offset] ^ PCW[j];
}
} else if ((d_fr_type == FT_2V) || (d_fr_type == FT_4V)) {
} else if (d_pr_type == PT_P25_PHASE2) {
//TDMA
offset += (d_adp_position * 7) + 256;
d_adp_position = (d_adp_position + 1) % 18;
for (int j = 0; j < 7; ++j) {
PCW[j] = adp_keystream[j + offset] ^ PCW[j];
}
Expand Down
13 changes: 7 additions & 6 deletions lib/op25_repeater/lib/p25_crypt_algs.h
Original file line number Diff line number Diff line change
Expand Up @@ -36,24 +36,25 @@ struct key_info {
std::vector<uint8_t> key;
};

enum frame_type { FT_UNK = 0, FT_LDU1, FT_LDU2, FT_2V, FT_4V };
enum frame_type { FT_UNK = 0, FT_LDU1, FT_LDU2, FT_2V, FT_4V_0, FT_4V_1, FT_4V_2, FT_4V_3 };
enum protocol_type { PT_UNK = 0, PT_P25_PHASE1, PT_P25_PHASE2 };

class p25_crypt_algs
{
private:
log_ts& logts;
int d_debug;
int d_msgq_id;
frame_type d_fr_type;
protocol_type d_pr_type;
uint8_t d_algid;
uint16_t d_keyid;
uint8_t d_mi[9];
std::unordered_map<uint16_t, key_info> d_keys;
std::unordered_map<uint16_t, key_info>::const_iterator d_key_iter;
uint8_t adp_keystream[469];
int d_adp_position;
uint32_t d_adp_position;

bool adp_process(packed_codeword& PCW);
bool adp_process(packed_codeword& PCW, frame_type fr_type, int voice_subframe);
void adp_keystream_gen();
void adp_swap(uint8_t *S, uint32_t i, uint32_t j);

Expand All @@ -62,8 +63,8 @@ class p25_crypt_algs
~p25_crypt_algs();

void key(uint16_t keyid, uint8_t algid, const std::vector<uint8_t> &key);
bool prepare(uint8_t algid, uint16_t keyid, frame_type fr_type, uint8_t *MI);
bool process(packed_codeword& PCW);
bool prepare(uint8_t algid, uint16_t keyid, protocol_type pr_type, uint8_t *MI);
bool process(packed_codeword& PCW, frame_type fr_type, int voice_subframe);
void reset(void);
inline void set_debug(int debug) {d_debug = debug;}
};
Expand Down
11 changes: 9 additions & 2 deletions lib/op25_repeater/lib/p25p1_fdma.cc
Original file line number Diff line number Diff line change
Expand Up @@ -404,6 +404,7 @@ namespace gr {

void p25p1_fdma::process_TTDU() {
process_duid(framer->duid, framer->nac, NULL, 0);
reset_ess();

if ((d_do_imbe || d_do_audio_output) && (framer->duid == 0x3 || framer->duid == 0xf)) { // voice termination
op25audio.send_audio_flag(op25_audio::DRAIN);
Expand Down Expand Up @@ -654,7 +655,7 @@ namespace gr {
void p25p1_fdma::process_voice(const bit_vector& A, const frame_type fr_type) {
if (d_do_imbe || d_do_audio_output) {
if (encrypted())
crypt_algs.prepare(ess_algid, ess_keyid, fr_type, ess_mi);
crypt_algs.prepare(ess_algid, ess_keyid, PT_P25_PHASE1, ess_mi);

for(size_t i = 0; i < nof_voice_codewords; ++i) {
voice_codeword cw(voice_codeword_sz);
Expand All @@ -680,7 +681,7 @@ namespace gr {
if (encrypted()) {
packed_codeword ciphertext;
imbe_pack(ciphertext, u[0], u[1], u[2], u[3], u[4], u[5], u[6], u[7]);
audio_valid = crypt_algs.process(ciphertext);
audio_valid = crypt_algs.process(ciphertext, fr_type, i);
imbe_unpack(ciphertext, u[0], u[1], u[2], u[3], u[4], u[5], u[6], u[7]);
}

Expand Down Expand Up @@ -777,6 +778,12 @@ namespace gr {
qtimer.reset();
}

void p25p1_fdma::call_end() {
if (d_do_audio_output)
op25audio.send_audio_flag(op25_audio::DRAIN);
reset_ess();
}

void p25p1_fdma::crypt_reset() {
crypt_algs.reset();
}
Expand Down
2 changes: 2 additions & 0 deletions lib/op25_repeater/lib/p25p1_fdma.h
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,7 @@ namespace gr {
void process_frame();
void check_timeout();
inline bool encrypted() { return (ess_algid != 0x80); }
inline void reset_ess() { ess_algid = 0x80; memset(ess_mi, 0, sizeof(ess_mi)); }
void send_msg(const std::string msg_str, long msg_type);

// internal instance variables and state
Expand Down Expand Up @@ -116,6 +117,7 @@ namespace gr {
void set_debug(int debug);
void set_nac(int nac);
void reset_timer();
void call_end();
void crypt_reset();
void crypt_key(uint16_t keyid, uint8_t algid, const std::vector<uint8_t> &key);
void rx_sym (const uint8_t *syms, int nsyms);
Expand Down
Loading
Loading