Este programa en asembler es para el 876, pero si cambias las normativas a 877 creo que casi no debes cambiar mas nada, por las dudas controla que el tris esté correcto con respecto al tuyo.
Es un programa para generar 40khz, pero si cambias el periodo y duty cambias la frecuencia.
LIST p=16f876a ;list directive to define processor
#include <p16f876a.inc> ;processor specific definitions
;Observa que los parámetros de configuración son los que te sirven a tu proyecto
__config _CP_OFF & _XT_OSC & _WDT_OFF & _PWRTE_ON & _LVP_OFF & _BODEN_OFF
;Parámetros para eliminar los mensajes de warning cuando lo ensamblas
ERRORLEVEL -302 ;suppress "not in bank 0" message
ERRORLEVEL -203 ;suppress message
ERRORLEVEL -305 ;suppress message
ERRORLEVEL -205 ;suppress message
#define PWM PORTC,2 ; pin salida audio RC2/CCP1, pin 13 del micro
; lo suyo sería ingresar esta señal a un transformador pequeño de relación
; 8-200 para aumentar la potencia de salida hacia el transductor
; aunque no es necesario definir el pin de salida lo hago con motivo informativo
;Constantes para la onda de salida. Con estos valores obtienes 40khz medidos con osciloscopio.
; Si necesitas otra frecuencia no tienes mas que subir o bajar ambos valores. Ten en cuenta
; que el duty deberá ser siempre la mitad del valor del período para obtener una onda cuadrada
; Si subes los valores obtendrás una frecuencia más baja.
periodo equ .48 ; PWM periodo, lo que ocupa un flanco de subida y uno de bajada (un 1 y un 0)
duty equ .25 ; PWM duty del ciclo, el tiempo que está en 1
ORG 0x00
goto init ;ir al inicio del programa
ORG 0x05
;Inicializar micro
init clrf PORTA ;clear port A
clrf PORTB ;clear port B
clrf PORTC ;clear port C
bsf STATUS,RP0
bcf STATUS,RP1 ;bank 1
movlw 0x06
movwf ADCON1 ;set puerto analógico como digital
movlw b"11111111" ; He puesto todos los pins
movwf TRISA ; de todos los puertos como entradas (1)
movlw b"11111111" ; salvo el pin RC2 que está como salida (0)
movwf TRISB
movlw b"11111011"
movwf TRISC
bcf STATUS,RP0 ;switch bank 0
bsf STATUS,RP0 ;switch bank 1
movlw periodo ; cargamos el valor del período en PR2
movwf PR2
bcf STATUS,RP0 ;switch bank 0
movlw duty ; cargamos valor del duty en CCPR1L
movwf CCPR1L
Principal
; Ya está listo para emitir. Sólo debes poner estas 3 lineas para activar la salida
pwmon bsf T2CON,2 ;TMR2 activado
movlw 0x0c ;cargamos setup módulo
movwf CCP1CON ;PWM
; Esta linea para que quede emitiendo. Puedes reemplazarla por una pausa, una activación por botón, etc etc.
loop nop
goto loop
; Estas lineas para desactivar la salida
pwmoff clrf CCP1CON
bcf T2CON,2 ;Desactivamos TMR2
bcf PWM ;esta línea en caso que al finalizar la emisión el pin quede a 1.
;Y ya está.
; Se podría hacer por pin común on/off con pausas para generar la onda,
;sin usar el módulo PWM pero es una pena tener ese módulo y no usarlo.
; Además ya queda como ejemplo para usos futuros de los foristas
end