Guillermo,
Para recordar valores podes tener "reservada" cierta región de la memoria para manetener el estado que se quiera. Desde assembler se podría por ejemplo definir algunas variables en memoria (ver directivas db, dw, ddw) o cierto rango de direcciones con dup.
Luego en la rutina podés consultar y modificar esas variables que a priori son parte de tu programa por lo que no deberían ser modificadas nadie (x ej una interrupción de un tercero no debería modificar esos datos).
Ahora van algunos comentarios sobre las otras ideas que tuviste:
Lo de usar entrada/salida requiere que tengas algún dispositivo que interactúe por lo que salvo que tengas algún hardware adicional no vas a poder usarlo para persistir estado.
Lo de modificar el código hoy en día está muy mal visto e incluso en arquitecturas más modernas no vas a poder modificar el código salvo que tengas permisos especiales. En 8086 sí podes hacerlo porque no hay protección de memoria. En ese caso estarías modificando el propio programa, en particular en tu ejemplo es un parámetro a la instrucción MOV. En su tiempo (hace ~30 años) era bastante común encontrar código automodificable, hoy en día no. Para obtener el CS y el IP no hay que usar un JMP sino un CALL far a una rutina que mire el tope del stack para obtener "CS" e "IP" del llamador, o un CALL near para obtener solamente el "IP".
Saludos,
Gustavo