⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 keyer-3.0.18.asm

📁 PIC16F628A制作的自动键程序,供无线电爱好者参考.
💻 ASM
📖 第 1 页 / 共 5 页
字号:
	movlw 0x02					; exiting dit
	call pause_w_100ms
	bsf sending_dit
	call send_dit_or_dah
		
	bcf dit_buffer				; clean out buffers in case they got set in loop_cw_unit
	bcf dah_buffer
	
	return
	
tune_dit_pressed
	bcf tune_latch_mode		; get out of latch mode
	ifdef include_txwake_line_code
	bsf txwake
	endif
	bsf key					; key tx
	ifdef include_toggle_sidetone_on_off_code
	btfss sidetone_off_during_tx
	endif ;include_toggle_sidetone_on_off_code
	bsf sidetone			; key sidetone
	call loop_cw_unit		;
	goto tune_mode_check_for_exit
	
tune_dah_pressed
	bsf tune_latch_mode		; go into latch mode
	btfss key
	goto tune_key
	bcf key
	bcf sidetone
	call pause_100_ms
	ifdef include_txwake_line_code
	bcf txwake
	endif
	goto tune_dah_pressed_loop
tune_key
	ifdef include_txwake_line_code
	bsf txwake
	endif
	bsf key
	ifdef include_toggle_sidetone_on_off_code
	btfss sidetone_off_during_tx
	endif ;include_toggle_sidetone_on_off_code
	bsf sidetone
	call loop_cw_unit		;

tune_dah_pressed_loop		; wait for dah to be released
	call loop_cw_unit
	btfss dit						; if dit is pressed,
	goto tune_mode_check_for_exit	;  blow out of the loop because both dit and dah are squeezed
	btfss dah				; if dah is not pressed, skip over
	goto tune_dah_pressed_loop

	goto tune_mode_check_for_exit

	endif ;include_tune_mode_code

; ------------------	

	ifdef include_calibration_code

calibration_check_mode

	; this mode allows you to check the cw unit timing calibration
	; hold down the dit paddle for a minute or half minute
	; after releasing the paddle, the number of dits will be announced in CW
	; use the formula below to determine the proper number of dits for the wpm setting
	; speed in wpm = dits per min / 25
	; 20 WPM equals 500 dits per minute or 250 dits per 20 seconds

	clrf binary2bcd_binary_in+0
	clrf binary2bcd_binary_in+1
	bsf sending_dit

calibration_check_mode_wait_loop
	btfsc dit							; loop while waiting for dit to be pressed
	goto calibration_check_mode_wait_loop
calibration_dit_loop
	call send_dit_or_dah				; send a dit
	incf binary2bcd_binary_in+1, F		; increment the dit counter
	btfsc STATUS, Z						; did the lower byte roll over ?
	incf binary2bcd_binary_in+0, F		; if so, increment the upper byte
	btfss dit							; if dit is still pressed
	goto calibration_dit_loop			;   continue to loop
	
	movlw 0x05
	call pause_w_100ms
	
	call binary2bcd

	; break out lower nibble of middle BCD digit
	movfw BCD1
	andlw b'00001111'
	movwf bcd_low_nibble
	addwf bcd_low_nibble, F 	; double it so we're in the right spot in cw_table

	movfw bcd_low_nibble		; send the low nibble BCD digit in CW
	call cw_table
	movwf cw_char_to_send+0
	movfw bcd_low_nibble
	addlw 0x01
	call cw_table
	movwf cw_char_to_send+1
	errorlevel -306
	pagesel send_cw
	call send_cw
	errorlevel +306

	; send least signficant BCD digit
	call send_BCD2_in_cw

	return	
	

	endif
; ------------------



program_memory

	; parms
	;	memory_number (0 = callsign memory)
	;
	; calls
	;	send_dit_or_dah
	;	check_paddles
	;	pause_w_100ms
	;	divide16bit

	; send a dit or boop_beep to signify start	
	movlw 0x02
	call pause_w_100ms
	ifdef include_funky_beeps_code
	call boop_beep
	else
	bsf sending_dit
	call send_dit_or_dah
	endif

	; initialize counters
	clrf cw_unit_count

	bcf temp_memory_dirty
		
	movlw b'11000000'
	movwf temp_memory_mask
	clrf temp_memory

	; get parameters for this memory
	movlw eeprom_memory_locations			; get the *address* of memory location array
	movwf FSR
	movfw memory_number						; add for the appropriate memory location
	addwf FSR, F		
	movfw INDF
	movwf temp_memory_eeprom_pointer		; initialize the live eeprom pointer
	movwf start_of_memory_location			; initialize the static starting location
	incf temp_memory_eeprom_pointer, F		; actual recording starts at +1
	

initial_recording_loop	
	; check if mode button was hit
	pagesel we_are_done_with_programming
	errorlevel -306
	btfss mode_switch
	goto we_are_done_with_programming
	errorlevel +306
	pagesel check_paddles
	errorlevel -306
	call check_paddles
	errorlevel +306
	btfsc dit_buffer
	goto add_dit_or_dah_to_memory
	btfsc dah_buffer
	goto add_dit_or_dah_to_memory
	goto initial_recording_loop	
	
init_recording_loop_counters
	movlw 0x00
	movwf recording_loop_counter1
	movwf recording_loop_counter2

recording_loop
	ifdef include_function_button_code
	btfss switch0
	goto we_are_done_with_programming
	btfss switch1
	goto we_are_done_with_programming
	btfss switch2
	goto we_are_done_with_programming
	endif
	pagesel we_are_done_with_programming
	errorlevel -306
	btfss mode_switch
	goto we_are_done_with_programming
	errorlevel +306
	pagesel check_paddles
	errorlevel -306
	call check_paddles
	errorlevel +306
	btfsc dit_buffer
	goto store_cw_unit_in_temp_memory
	btfsc dah_buffer
	goto store_cw_unit_in_temp_memory
	; nothing is active right now, increment the inactive counters
	incfsz recording_loop_counter1, F
	goto recording_loop
	movfw recording_loop_counter2
	sublw 0xFF							
	btfss STATUS, Z						
	incf recording_loop_counter2, F
	goto recording_loop
	
we_are_done_with_programming
	; store the last byte if temp_memory is dirty
	btfsc temp_memory_dirty
	call store_temp_memory_to_eeprom
	movfw cw_unit_count				;see if cw_unit_count is zero
	btfsc STATUS,Z
	decf cw_unit_count,F			;if so, store FF in cw_unit_count to signify blank memory
	; store the cw_unit_count in the first byte
	movfw start_of_memory_location
	errorlevel -302
	banksel EEADR
	movwf EEADR
	errorlevel +302
	banksel PORTA
	movfw cw_unit_count
	errorlevel -302
	banksel EEDATA
	movwf EEDATA
	errorlevel +302
	banksel PORTA
	call write_eeprom
	movlw 0x03
	call pause_w_100ms
	ifdef include_funky_beeps_code
	call beep_boop
	else
	bsf sending_dit
	call send_dit_or_dah
	endif
	return ; we are totally done

    ;------------- sub-subroutines


store_cw_unit_in_temp_memory

	; store the silent timee before the cw_unit
	; first, calculate the ratio between the silent and the cw unit time
	movfw cw_unit_counter+1
	movwf divisor+1
	movfw cw_unit_counter+0
	movwf divisor+0
	movfw recording_loop_counter1	; recording_loop_counter / cw_unit_counter = space ratio
	movwf dividend+1				; this is used below to determine if we have an intercharacter space
	movfw recording_loop_counter2	; or an interword space
	movwf dividend+0
	call divide16bit
	movfw quotient+0				; check if quotient MSB is zero
	btfsc STATUS, Z		
	goto measure_up_silent_time		; if so, skip over this stuff
	movlw 0xff						; if not, set LSB to FF
	movwf quotient

measure_up_silent_time
	movfw quotient+1	; see how many cw_unit lengths we had silent before this cw_unit
	sublw d'1'							; is this an intercharacter space ? was 10
	btfsc STATUS, C						
	goto add_dit_or_dah_to_memory		; no, it's negative, don't add a space cw_unit
	movfw quotient+1					; is this an interword space ?
	sublw d'14'							; was 70
	btfsc STATUS, C
	goto skip_over_1					; result is negative, we have less than 6 cw_units
	movlw b'00000000'					; 00 = 6 cw_unit space
	goto skip_over_2
skip_over_1
	movlw b'10101010'					; 10 = 2 cw_unit space
skip_over_2
	call store_w_in_temp_memory

add_dit_or_dah_to_memory
	btfss dit_buffer
	goto skip_over_dit
	bsf sending_dit
	call send_dit_or_dah
	movlw b'01010101'	; 01 = dit
	bcf dit_buffer		; clean out dit buffer
	goto skip_over_dah
skip_over_dit
	bcf sending_dit
	call send_dit_or_dah
	movlw b'11111111'	; 11 = dah
	bcf dah_buffer		; clean out dah buffer
skip_over_dah
	call store_w_in_temp_memory
	
	; enforce cw unit limit count so we don't run over into another memory
	; get cw_unit count limit
	movlw eeprom_memory_loc_limits+0
	movwf FSR
	movfw memory_number						; add for the appropriate memory location
	addwf FSR, F		
	movfw INDF
	subwf cw_unit_count, W					; does cw_unit_count = cw_unit count limit ?
	btfss STATUS, Z
	goto init_recording_loop_counters 		; no, go back for more
	bsf sidetone							; yes, lock up the sidetone
wait_for_user_to_realize	
	ifdef include_funky_beeps_code
	call low_beep
	endif
	call pause_100_ms
	btfss dit
	goto wait_for_user_to_realize
	btfss dah
	goto wait_for_user_to_realize
	bcf sidetone
	bcf dit_buffer
	bcf dah_buffer
	goto we_are_done_with_programming
		
	;cleanup

store_w_in_temp_memory
	andwf temp_memory_mask, W			; apply the mask to W
	addwf temp_memory, F				; add the cw_unit to temp_memory
	;increment cw_unit count	
	incf cw_unit_count, F	

;setup_for_next_store_w
	bsf temp_memory_dirty
	rrf temp_memory_mask, F				; move the bit mask over
	rrf temp_memory_mask, F
	btfsc STATUS, C						; if we carried, we need to start a new byte
	call store_temp_memory_to_eeprom
	return

store_temp_memory_to_eeprom
	movwf temp_w	; preserve w
	; write the temp memory byte to eeprom
	movfw temp_memory_eeprom_pointer
	errorlevel -302
	banksel EEADR
	movwf EEADR
	errorlevel +302
	banksel PORTA
	movfw temp_memory
	errorlevel -302
	banksel EEDATA
	movwf EEDATA
	errorlevel +302
	banksel PORTA
	errorlevel -306
	pagesel check_paddles
	call check_paddles
	errorlevel +306
	call write_eeprom
	errorlevel -306
	pagesel check_paddles
	call check_paddles
	errorlevel +306
	;get things ready for new byte
	movlw b'11000000'
	movwf temp_memory_mask
	clrf temp_memory
	; point to the next eeprom byte to be written
	incf temp_memory_eeprom_pointer, F
	; TODO - check if we're at the limit for this memory
	movfw temp_w	; restore w
	bcf temp_memory_dirty
	return

;	endif
	
; ------------------

read_eeprom

	; read eeprom address in w
	; return data in w
	errorlevel -302
	banksel EEADR
	movwf EEADR
	banksel EECON1
	bsf EECON1, RD		
	banksel EEDATA
	movfw EEDATA
	errorlevel +302
	banksel PORTA
	return

; ------------------

check_for_button_hit
	btfss dit
	retlw 1
	btfss dah
	retlw 1
	btfss mode_switch
	retlw 1
	ifdef include_function_button_code
	btfss switch0
	retlw 1
	btfss switch1
	retlw 1
	btfss switch2
	retlw 1
	endif
	retlw 0

; ------------------

loop_check_for_button_hit
	call check_for_button_hit
	sublw 0x01
	btfsc STATUS,Z
	goto loop_check_for_button_hit
	call pause_100_ms
	return

; ------------------

play_memory

	ifdef include_function_button_code
	bcf memory_playback_manual_exit			; clear flag to tell calling subroutines if user manaully exited
	endif
	
	; get parameters for this memory
	movlw eeprom_memory_locations			; get the *address* of memory location array
	movwf FSR
	movfw memory_number						; add for the appropriate memory location
	addwf FSR, F		
	movfw INDF
	movwf temp_memory_eeprom_pointer		; initialize the live eeprom pointer
	; read the cw_unit count for this memory	
	call read_eeprom
	movwf cw_unit_count

	; check for blank memory	
	movlw 0xFF
	subwf cw_unit_count, W	; is the cw_unit count 0xFF ?
	btfss STATUS, Z
	goto byte_loop			; no, skip over this
	ifdef include_funky_beeps_code
	call low_beep
	else
	bsf sending_dit			; yes, send three dits and blow out
	bcf key_tx_active
	call send_dit_or_dah
	call send_dit_or_dah
	call send_dit_or_dah
	bsf key_tx_active
	endif ;include_funky_beeps_code
	return

byte_loop
	; get a byte from eeprom
	incf temp_memory_eeprom_pointer, F	; move to the next byte
	movfw temp_memory_eeprom_pointer
	call read_eeprom
	movwf temp_memory
	movlw 0x04				; four cw_units in a byte
	movwf temp_memory_mask	; use temp_memory_mask as a cw_unit within a byte counter
cw_unit_loop
	; TODO - exit if a switch or paddle is hit


	rlf temp_memory, F
	btfsc STATUS, C
	goto first_bit_1
;first_bit_0
	rlf temp_memory, F
	btfsc STATUS, C
	goto cw_unit_01
;cw_unit_00	- 6 cw_unit space
	call loop_cw_unit
	call loop_cw_unit
	call loop_cw_unit
	call loop_cw_unit	
	call loop_cw_unit
	call loop_cw_unit
	goto next_cw_unit_setup
first_bit_1
	rlf temp_memory, F
	btfsc STATUS,C
	goto cw_unit_11
;cw_unit_10 - 2 cw_unit space
	call loop_cw_unit
	call loop_cw_unit
	goto next_cw_unit_setup	
cw_unit_11 ; dah
	bcf sending_dit
	call send_dit_or_dah
	goto next_cw_unit_setup
cw_unit_01
	bsf sending_dit
	call send_dit_or_dah
next_cw_unit_setup
	decf cw_unit_count, F
	btfsc STATUS, Z				; did we do the last cw_unit ?
	return						; yes, blow out
	call check_for_button_hit
	sublw 0x01
	btfsc STATUS,Z
	goto button_hit_loop
	decf temp_memo

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -