diff loadtools/audump.c @ 852:8a89a42baa70

fc-loadtool tfc139-audio-dump hack implemented
author Mychaela Falconia <falcon@freecalypso.org>
date Sat, 09 Oct 2021 21:24:51 +0000
parents loadtools/ltmisc.c@dfe6ba3611cd
children
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/loadtools/audump.c	Sat Oct 09 21:24:51 2021 +0000
@@ -0,0 +1,139 @@
+/*
+ * This module implements the tfc139-audio-dump command in fc-loadtool,
+ * which is a special hack for reverse engineering of Compal audio configs.
+ * This hack command is named so because it will only produce interesting
+ * output if fc-loadtool has been entered via tfc139, i.e., breaking into
+ * a running Compal firmware.
+ */
+
+#include <sys/types.h>
+#include <stdio.h>
+#include <stdint.h>
+#include <stdlib.h>
+#include <string.h>
+#include <strings.h>
+
+extern char target_response_line[];
+
+do_abbr(page, reg, retptr)
+	unsigned page, reg;
+	uint16_t *retptr;
+{
+	char page_arg[8], reg_arg[8], *argv[4];
+	int stat;
+	char *strtoul_endp;
+
+	sprintf(page_arg, "%u", page);
+	sprintf(reg_arg, "%u", reg);
+	argv[0] = "abbr";
+	argv[1] = page_arg;
+	argv[2] = reg_arg;
+	argv[3] = 0;
+	tpinterf_make_cmd(argv);
+	if (tpinterf_send_cmd() < 0)
+		return(-1);
+	stat = tpinterf_capture_output_oneline(1);
+	if (stat != 1) {
+errout:		fprintf(stderr, "error: malformed response to abbr command\n");
+		return(-1);
+	}
+	if (strlen(target_response_line) != 3)
+		goto errout;
+	*retptr = strtoul(target_response_line, &strtoul_endp, 16);
+	if (strtoul_endp != target_response_line + 3)
+		goto errout;
+	return(0);
+}
+
+cmd_tfc139_audio_dump(argc, argv)
+	char **argv;
+{
+	uint16_t data[31];
+	int i, stat;
+	FILE *of;
+
+	if (argv[1]) {
+		of = fopen(argv[1], "w");
+		if (!of) {
+			perror(argv[1]);
+			return(-1);
+		}
+	} else
+		of = stdout;
+	/* read d_aec_ctrl */
+	stat = do_r16(0xFFD00238, data);
+	if (stat) {
+bad_read:	if (argv[1])
+			fclose(of);
+		return(stat);
+	}
+	fprintf(of, "d_aec_ctrl: 0x%04X\n", (int) data[0]);
+	/* read new AEC parameter words */
+	for (i = 0; i < 8; i++) {
+		stat = do_r16(0xFFD0084A + (i << 1), data + i);
+		if (stat)
+			goto bad_read;
+	}
+	fputs("New AEC params:", of);
+	for (i = 0; i < 8; i++)
+		fprintf(of, " 0x%04X", (int) data[i]);
+	putc('\n', of);
+	putc('\n', of);
+	/* read UL FIR coeffs */
+	for (i = 0; i < 31; i++) {
+		stat = do_r16(0xFFD00908 + (i << 1), data + i);
+		if (stat)
+			goto bad_read;
+	}
+	fputs("Uplink FIR coefficients:\n", of);
+	for (i = 0; i < 31; i++) {
+		if (i == 0 || i == 8 || i == 16 || i == 24)
+			putc('\n', of);
+		else
+			putc(' ', of);
+		fprintf(of, "0x%04X", (int) data[i]);
+	}
+	putc('\n', of);
+	putc('\n', of);
+	/* read DL FIR coeffs */
+	for (i = 0; i < 31; i++) {
+		stat = do_r16(0xFFD00946 + (i << 1), data + i);
+		if (stat)
+			goto bad_read;
+	}
+	fputs("Downlink FIR coefficients:\n", of);
+	for (i = 0; i < 31; i++) {
+		if (i == 0 || i == 8 || i == 16 || i == 24)
+			putc('\n', of);
+		else
+			putc(' ', of);
+		fprintf(of, "0x%04X", (int) data[i]);
+	}
+	putc('\n', of);
+	putc('\n', of);
+	/* read ABB VBC registers */
+	stat = do_abbr(1, 8, data);
+	if (stat)
+		goto bad_read;
+	fprintf(of, "VBCTRL1: 0x%03X\n", (int) data[0]);
+	stat = do_abbr(1, 11, data);
+	if (stat)
+		goto bad_read;
+	fprintf(of, "VBCTRL2: 0x%03X\n", (int) data[0]);
+	stat = do_abbr(1, 10, data);
+	if (stat)
+		goto bad_read;
+	fprintf(of, "VBPOP:   0x%03X\n", (int) data[0]);
+	stat = do_abbr(1, 7, data);
+	if (stat)
+		goto bad_read;
+	fprintf(of, "VBUCTRL: 0x%03X\n", (int) data[0]);
+	stat = do_abbr(0, 6, data);
+	if (stat)
+		goto bad_read;
+	fprintf(of, "VBDCTRL: 0x%03X\n", (int) data[0]);
+	/* done */
+	if (argv[1])
+		fclose(of);
+	return(0);
+}