def main(): # Reed message from file and encode msg = open('data/input.txt', 'r').read().encode() msgs = split_str(msg, n - 2 * t) # Open timer file in append mode encode_time = open('data/encode_time_python.csv', 'a') decode_time = open('data/decode_time_python.csv', 'a') # Generate table and generater polynomial # prim = rs.find_prime_polys(c_exp=m, fast_primes=True, single=True) # rs.init_tables(c_exp=m, prim=prim) rs.init_tables(0x14d) gen = rs.rs_generator_poly_all(n) for i in range(runs): # Encode msg msgeccs = [] t1 = time.perf_counter() for m in msgs: msgeccs.append(rs.rs_encode_msg(m, 2 * t, gen=gen[2 * t])) t2 = time.perf_counter() encode_time.write(str(t2 - t1) + '\n') # Error for msgecc in msgeccs: error_inject(msgecc) # Decode corrections = [] t1 = time.perf_counter() for msgecc in msgeccs: corrections.append(rs.rs_correct_msg(msgecc, 2 * t)) t2 = time.perf_counter() decode_time.write(str(t2 - t1) + '\n') rmsg = b'' for c in corrections: rmsg += c[0] # Check result if (msg.decode() == rmsg.decode()): print("True") else: print("False")
# poscorrup=random.sample(range(0, 128), i/2) # for j in range(0,len(poscorrup)): # enc[j]=random.randint(0,100) # start_time = time.time() # dec=rs.decode(enc) # end_time = time.time() # #print("msg= ", msg) # #print("enc= ", enc) # #print("dec= ", dec) # if msg==dec: # print("Success decoding RS<%d,%d> time = %f " %(255-i,i,end_time-start_time)) # else: # print("fail") prim = rs.find_prime_polys(c_exp=12, fast_primes=True, single=True) rs.init_tables(c_exp=12, prim=prim) n = 255 nsym = 12 mes = "a" * (n-nsym) #mesbytarray=[elem.encode(decimal.Decimal) for elem in mes] gen = rs.rs_generator_poly_all(n) print(len(gen)) enc = rs.rs_encode_msg(mes, nsym, gen=gen[nsym]) enc[1] = 0 enc[2]=0 enc[4]=0 enc[8]=0 enc[32] = 0 enc[33]=0 rmes, recc = rs.rs_correct_msg(enc, nsym, erase_pos=None)
# Calculation of packet decoding probability def PDP(p, N, nk): min = (nk / 2) + 1 pdp = 0 for k in range(min, N + 1): # Calculate PDP with the formula from literature pdp += (float(factorial(N)) / (factorial(k) * factorial(N - k))) * (p**k) * ( (1 - p)**(N - k)) return 1 - pdp # Init reedsolo.init_tables(0x11d) # Probability of errors #pe = [0.1, 0.25, 0.5, 0.75, 1] pe = [0.001, 0.01, 0.03, 0.05, 0.1, 0.15, 0.25, 0.40, 0.5] petrace = pe + [1] # Number of packets to test for each probability n = 10000 #nkarr= [2] nkarr = [2, 8, 18] for nfig in range(len(nkarr)): # Packet to be tested nk = nkarr[nfig] packet = reedsolo.rs_encode_msg('123456789', nk)
#!/usr/bin/env python3 # vim: set ts=4 sw=4 tw=0 et pm=: import reedsolo # IIQ/LCW3: Message: 31B, checksum: 8B, erasure: 8B - RS(47,31) [total: 312b] generator=2 fcr=0 # first consecutive root nsym=8 # number of ecc symbols (n-k) elen=8 # erasure length (how many bytes erased at end) c_exp=8 # bits per symbol prim=0x11d reedsolo.init_tables(prim=prim,generator=generator,c_exp=c_exp) def rs_check(data): mlen=len(data)-nsym msg=reedsolo.rs_encode_msg(data[:mlen],nsym+elen,fcr=fcr) return bytearray(data[mlen:])==msg[mlen:len(data)] def rs_fix(data): # data=data+bytearray([0]*elen) data=data+([0]*elen) r=list(range(len(data)-elen,len(data))) try: (cmsg,crs)=reedsolo.rs_correct_msg(data,nsym+elen,fcr,generator,erase_pos=r) except reedsolo.ReedSolomonError: return (False,None,None) except ZeroDivisionError: return (False,None,None)
#parameters c_exp = 20 max_length = 2**c_exp - 1 init_message_len = 10 #generate a prime for large field print("generating a prime for large field") start_time1 = time.time() prim = rs.find_prime_polys(c_exp=c_exp, fast_primes=True, single=True) end_time1 = time.time() prime_poly_time = end_time1 - start_time1 print("Time Prime polynomial generation", prime_poly_time) #initilaize to log and exponenent tables and genrate polynomials start_time2 = time.time() print("initializing tables") rs.init_tables(c_exp=c_exp, prim=prim) end_time2 = time.time() # gf_exp=open('exp.pkl', 'r') # gf_log=open('log.pkl', 'r') # rs.gf_exp=pickle.load(gf_exp) # rs.gf_log=pickle.load(gf_log) start_time3 = time.time() # gf_exp.close() # gf_log.close() print("generating polynomial") #gen = rs.rs_generator_poly_all(2**c_exp - 1) end_time3 = time.time() table_init_time = end_time2 - start_time2 poly_gen_time = end_time3 - start_time3 print("TIME table initilaization ", table_init_time)
def place_data(base: QRMatrix, raw_data_code: List, rs_block_info: List, error_code_word_count: int, mask_id: int) -> QRMatrix: """ Places data on QRMatrix, and RETURNS DATA PART ONLY. :param mask_id: :param error_code_word_count: :param base: Base QRMatrix, THIS HAS TO HAVE ALL THE NECESSARY MODULES READY!! :param raw_data_code: RAW DATA, DO NOT INCLUDE ERROR CORRECTING CODES! :param rs_block_info: List of Tuple of (RS block data code count, number of that RS blocks.) :return: """ data_code = copy.deepcopy(raw_data_code) rs_blocks = [] # split the data code according to the RS block information. current_index = 0 for info in rs_block_info: word_count = info[0] repeat_count = info[1] for _ in range(repeat_count): rs_blocks.append(data_code[current_index:current_index + word_count]) current_index = current_index + word_count # For each data code, calculate the error codes. ecc_word_count = int(error_code_word_count / len(rs_blocks)) rs_block_error_codes = [] rs.init_tables(0x11d) for rs_block in rs_blocks: total_length = len(rs_block) + ecc_word_count gen = rs.rs_generator_poly_all(total_length) mesecc = rs.rs_encode_msg(rs_block, ecc_word_count, gen=gen[ecc_word_count]) print([x for x in gen[ecc_word_count]]) rs_block_error_codes.append(mesecc) # i_fx = copy.deepcopy(rs_block) # i_fx = i_pad_codes(i_fx, gx_word_count) # rs_block_error_codes.append(i_galois_division(i_fx, GaloisDividerDictionary.get_divider_for(gx_word_count))) binary_code = [] # First, interleave all the rs_blocks. code_index = 0 # earlier RS blocks may run out of data code at the end. in such case, carry on. while True: continue_count = 0 for block_id in range(len(rs_blocks)): if code_index >= len(rs_block_error_codes[block_id]): continue_count += 1 continue binary = convert_int_to_bool_array( rs_block_error_codes[block_id][code_index], 8) binary_code += binary if continue_count == len(rs_blocks): break code_index += 1 i_rs_block_error_codes = [x for x in rs_block_error_codes[0]] print(i_rs_block_error_codes) # +) 25*25 All matrix # -) 8*8*3 Placement Pattern # -) 5*5 Mini Placement Pattern # -) 9*2 Timing pattern # -) 15*2 Metadata error_area_start_index = len(data_code) * 8 # Then, we interleave all the rs_block_error_codes. """ code_index = 0 while True: continue_count = 0 for block_id in range(len(rs_block_error_codes)): if code_index >= len(rs_block_error_codes[block_id]): continue_count += 1 continue binary = convert_int_to_bool_array(rs_block_error_codes[block_id][code_index], 8) binary_code += binary if continue_count == len(rs_block_error_codes): break code_index += 1 """ data_buffer = QRMatrix(version=base.version) # How we place the data: # we start from bottom right. Then we decide which vertical direction to 'go when the situation requires first.' # (you can pick from up and down. We'll go UP this time) # After placing a bit in bottom right corner, we look at the two columns # (the one that you put the data + the one to the left.) # If you are currently on the right: # Try going LEFT. BUT if the fixed pattern is already sitting there, # You need to go whichever vertical direction you're going. # If this is the first one it's probably UP in this case # If you are currently on the left: # Look at the block to the current vertical direction. # If the block is vacant... # Go in that direction. If the right neighbour is vacant, place there. if not, place it here. # If the block is taken... # Try looking at the next neighbour in the current vertical direction. Do the same. # If you ran out of the space... # Give up going in the direction, go LEFT and place the bit there. # This ALSO causes the VERTICAL DIRECTION to FLIP! # we have created `buffer` all the way up. # FIRST INDEX IS DOWN, SECOND INDEX IS RIGHT. r = base.length - 1 c = base.length - 1 code_index = 0 is_going_up = True is_on_right = True while True: if code_index == error_area_start_index: print( "Error area is starting from row-wise {}, column-wise {}. We're going {} at this point" .format(r, c, "up" if is_going_up else "down")) # Place the data here assert base.value[r, c].is_null() assert data_buffer.value[r, c].is_null() # For masking reason, data will be saved in different place data_buffer.value[r, c] = QRModule.from_condition(binary_code[code_index]) # increment the index code_index = code_index + 1 if code_index == len(binary_code): break # Are you on the right? if is_on_right: # Try going to left... is it vacant? if base.value[r, c - 1].is_null(): c = c - 1 # then it's safe to put there is_on_right = False continue else: # Then try going into current vertical directions until you hit vacancy. while True: r = r + (-1 if is_going_up else 1) if base.value[r, c].is_null(): break assert 0 <= r < base.length, "You're not supposed to go out of the buffer like this." continue else: # You're on the left # Check the neighbouring block in current direction. checking_row = r while True: checking_row = checking_row + (-1 if is_going_up else 1) # if you end up running out of buffer during this process. # just go left and flip the direction. You're considered to be on right after this. if not (0 <= checking_row < base.length): # But be careful not to step on other data. checking_column = c - 1 checking_row = r while True: assert 0 <= checking_column < base.length, "You ran out of buffer in column direction" # try to find vacancy in the next left column. if base.value[checking_row, checking_column].is_null(): break checking_row = checking_row - 1 # If for some reason there are none, we need to check next column. # We preserve is_on_right at this point. if not (0 <= checking_row < base.length): checking_column = checking_column - 1 checking_row = r # reset checking row to try again r = checking_row c = checking_column is_going_up = not is_going_up is_on_right = True break # See the one to the right. is it vacant? if base.value[checking_row, c + 1].is_null(): # Right one is vacant! r = checking_row c = c + 1 is_on_right = True break elif base.value[checking_row, c].is_null(): # Left one is vacant! r = checking_row is_on_right = False break # Else, we need to continue going up or down. continue # return data_buffer for r in range(base.length): for c in range(base.length): # Some modules may not be used (e.g. Ver.5-Q, Binary mode.) # 'True vacancy,' which is occupied by neither data nor metadata, # seems to be treated as ON module - but we don't know for sure. if not base.value[r, c].is_null(): # We do not flip base value stuff. continue if data_buffer.value[r, c].is_null(): print("Null value detected at R: {0}, C: {1}, padded as True". format(r, c)) data_buffer.value[r, c] = QRModule.off() if MaskPattern.calculate(r, c, mask_id): if data_buffer.value[r, c].is_null(): print("Null value detected at R: {0}, C: {1}".format(r, c)) data_buffer.value[r, c].flip() return data_buffer
import sys import reedsolo reedsolo.init_tables(0x11d) qr_bytes = '''00100000 10100010 10111000 00111010 01011001 10011010 10001000 ???????? ???????? ???????? ???????? ???????? ???????? ???????? ???????? ??000000 11101100 00010001 11101100 00010001 11101100 00010001 00100100 1??????? ????????