Blame ld10k1/src/liblo10k1ef.c

Packit 427e91
/*
Packit 427e91
 *  EMU10k1 loader lib
Packit 427e91
 *  Copyright (c) 2003,2004 by Peter Zubaj
Packit 427e91
 *
Packit 427e91
 *
Packit 427e91
 *   This library is free software; you can redistribute it and/or modify
Packit 427e91
 *   it under the terms of the GNU Lesser General Public License as
Packit 427e91
 *   published by the Free Software Foundation; either version 2.1 of
Packit 427e91
 *   the License, or (at your option) any later version.
Packit 427e91
 *
Packit 427e91
 *   This program is distributed in the hope that it will be useful,
Packit 427e91
 *   but WITHOUT ANY WARRANTY; without even the implied warranty of
Packit 427e91
 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
Packit 427e91
 *   GNU Lesser General Public License for more details.
Packit 427e91
 *
Packit 427e91
 *   You should have received a copy of the GNU Lesser General Public
Packit 427e91
 *   License along with this library; if not, write to the Free Software
Packit 427e91
 *   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
Packit 427e91
 *
Packit 427e91
 */
Packit 427e91
 
Packit 427e91
#include <stdlib.h>
Packit 427e91
#include <stdio.h>
Packit 427e91
#include <string.h>
Packit 427e91
#include <sys/stat.h>
Packit 427e91
Packit 427e91
#include "ld10k1_error.h"
Packit 427e91
#include "ld10k1_fnc.h"
Packit 427e91
#include "comm.h"
Packit 427e91
#include "liblo10k1.h"
Packit 427e91
#include "liblo10k1ef.h"
Packit 427e91
Packit 427e91
#define AS10K1_FILE_SIGNATURE_ALSA "EMU10K1 FX8010 1"
Packit 427e91
#define AS10K1_FILE_SIGNATURE_EMU "emu10k1-dsp-file"
Packit 427e91
#define AS10K1_FILE_FORMAT_VERSION_EMU 1
Packit 427e91
Packit 427e91
liblo10k1_emu_patch_t *liblo10k1_emu_new_patch()
Packit 427e91
{
Packit 427e91
	liblo10k1_emu_patch_t *tmp = (liblo10k1_emu_patch_t *)malloc(sizeof(liblo10k1_emu_patch_t));
Packit 427e91
	
Packit 427e91
	if (!tmp)
Packit 427e91
		return NULL;
Packit 427e91
	memset(tmp, 0, sizeof(liblo10k1_emu_patch_t));
Packit 427e91
	
Packit 427e91
	return tmp;
Packit 427e91
}
Packit 427e91
Packit 427e91
void liblo10k1_emu_free_patch(liblo10k1_emu_patch_t *p)
Packit 427e91
{
Packit 427e91
	liblo10k1_emu_patch_set_in_count(p, 0);
Packit 427e91
	liblo10k1_emu_patch_set_out_count(p, 0);
Packit 427e91
	liblo10k1_emu_patch_set_dyn_count(p, 0);
Packit 427e91
	liblo10k1_emu_patch_set_sta_count(p, 0);
Packit 427e91
	liblo10k1_emu_patch_set_ctl_count(p, 0);
Packit 427e91
	liblo10k1_emu_patch_set_con_count(p, 0);
Packit 427e91
	liblo10k1_emu_patch_set_lookup_count(p, 0);
Packit 427e91
	liblo10k1_emu_patch_set_delay_count(p, 0);
Packit 427e91
	liblo10k1_emu_patch_set_instr_count(p, 0);
Packit 427e91
	
Packit 427e91
	free(p);
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_emu_patch_set_in_count(liblo10k1_emu_patch_t *p, int count)
Packit 427e91
{
Packit 427e91
	unsigned int *tmp = NULL;
Packit 427e91
	
Packit 427e91
	if (count > 0) {
Packit 427e91
		tmp = (unsigned int *)malloc(sizeof(unsigned int)*count);
Packit 427e91
		if (!tmp)
Packit 427e91
			return LD10K1_ERR_NO_MEM;
Packit 427e91
		memset(tmp, 0, sizeof(unsigned int) * count);
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	p->in_count = count;
Packit 427e91
	if (p->ins)
Packit 427e91
		free(p->ins);
Packit 427e91
	p->ins = tmp;
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_emu_patch_set_out_count(liblo10k1_emu_patch_t *p, int count)
Packit 427e91
{
Packit 427e91
	unsigned int *tmp = NULL;
Packit 427e91
	
Packit 427e91
	if (count > 0) {
Packit 427e91
		tmp = (unsigned int *)malloc(sizeof(unsigned int)*count);
Packit 427e91
		if (!tmp)
Packit 427e91
			return LD10K1_ERR_NO_MEM;
Packit 427e91
		memset(tmp, 0, sizeof(unsigned int) * count);
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	p->out_count = count;
Packit 427e91
	if (p->outs)
Packit 427e91
		free(p->outs);
Packit 427e91
	p->outs = tmp;
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_emu_patch_set_dyn_count(liblo10k1_emu_patch_t *p, int count)
Packit 427e91
{
Packit 427e91
	unsigned int *tmp = NULL;
Packit 427e91
	
Packit 427e91
	if (count > 0) {
Packit 427e91
		tmp = (unsigned int *)malloc(sizeof(unsigned int)*count);
Packit 427e91
		if (!tmp)
Packit 427e91
			return LD10K1_ERR_NO_MEM;
Packit 427e91
		memset(tmp, 0, sizeof(unsigned int) * count);
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	p->dyn_count = count;
Packit 427e91
	if (p->dyns)
Packit 427e91
		free(p->dyns);
Packit 427e91
	p->dyns = tmp;
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_emu_patch_set_sta_count(liblo10k1_emu_patch_t *p, int count)
Packit 427e91
{
Packit 427e91
	liblo10k1_emu_sc_t *tmp = NULL;
Packit 427e91
	
Packit 427e91
	if (count > 0) {
Packit 427e91
		tmp = (liblo10k1_emu_sc_t *)malloc(sizeof(liblo10k1_emu_sc_t) * count);
Packit 427e91
		if (!tmp)
Packit 427e91
			return LD10K1_ERR_NO_MEM;
Packit 427e91
		memset(tmp, 0, sizeof(liblo10k1_emu_sc_t)*count);
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	p->sta_count = count;
Packit 427e91
	if (p->stas)
Packit 427e91
		free(p->stas);
Packit 427e91
	p->stas = tmp;
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_emu_patch_set_ctl_count(liblo10k1_emu_patch_t *p, int count)
Packit 427e91
{
Packit 427e91
	liblo10k1_emu_ctl_t *tmp = NULL;
Packit 427e91
	
Packit 427e91
	if (count > 0) {
Packit 427e91
		tmp = (liblo10k1_emu_ctl_t *)malloc(sizeof(liblo10k1_emu_ctl_t) * count);
Packit 427e91
		if (!tmp)
Packit 427e91
			return LD10K1_ERR_NO_MEM;
Packit 427e91
		memset(tmp, 0, sizeof(liblo10k1_emu_ctl_t)*count);
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	p->ctl_count = count;
Packit 427e91
	if (p->ctls)
Packit 427e91
		free(p->ctls);
Packit 427e91
	p->ctls = tmp;
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_emu_patch_set_con_count(liblo10k1_emu_patch_t *p, int count)
Packit 427e91
{
Packit 427e91
	liblo10k1_emu_sc_t *tmp = NULL;
Packit 427e91
	
Packit 427e91
	if (count > 0) {
Packit 427e91
		tmp = (liblo10k1_emu_sc_t *)malloc(sizeof(liblo10k1_emu_sc_t) * count);
Packit 427e91
		if (!tmp)
Packit 427e91
			return LD10K1_ERR_NO_MEM;
Packit 427e91
		memset(tmp, 0, sizeof(liblo10k1_emu_sc_t)*count);
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	p->con_count = count;
Packit 427e91
	if (p->cons)
Packit 427e91
		free(p->cons);
Packit 427e91
	p->cons = tmp;
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_emu_patch_set_line_count(liblo10k1_emu_tram_t *t, int write, int count)
Packit 427e91
{
Packit 427e91
	liblo10k1_emu_tram_line_t *tmp = NULL;
Packit 427e91
	
Packit 427e91
	if (count > 0) {
Packit 427e91
		tmp = (liblo10k1_emu_tram_line_t *)malloc(sizeof(liblo10k1_emu_tram_line_t) * count);
Packit 427e91
		if (!tmp)
Packit 427e91
			return LD10K1_ERR_NO_MEM;
Packit 427e91
		memset(tmp, 0, sizeof(liblo10k1_emu_tram_line_t)*count);
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	if (write) {
Packit 427e91
		t->write_line_count = count;
Packit 427e91
		if (t->write_lines)
Packit 427e91
			free(t->write_lines);
Packit 427e91
		t->write_lines = tmp;
Packit 427e91
	} else {
Packit 427e91
		t->read_line_count = count;
Packit 427e91
		if (t->read_lines)
Packit 427e91
			free(t->read_lines);
Packit 427e91
		t->read_lines = tmp;
Packit 427e91
	}
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_emu_patch_set_lookup_count(liblo10k1_emu_patch_t *p, int count)
Packit 427e91
{
Packit 427e91
	liblo10k1_emu_tram_t *tmp = NULL;
Packit 427e91
	int i;
Packit 427e91
	
Packit 427e91
	if (count > 0) {
Packit 427e91
		tmp = (liblo10k1_emu_tram_t *)malloc(sizeof(liblo10k1_emu_tram_t) * count);
Packit 427e91
		if (!tmp)
Packit 427e91
			return LD10K1_ERR_NO_MEM;
Packit 427e91
		memset(tmp, 0, sizeof(liblo10k1_emu_tram_t)*count);
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	if (p->tram_lookups) {
Packit 427e91
		for (i = 0; i < p->tram_lookup_count; i++) {
Packit 427e91
			liblo10k1_emu_patch_set_line_count(&(p->tram_lookups[i]), 0, 0);
Packit 427e91
			liblo10k1_emu_patch_set_line_count(&(p->tram_lookups[i]), 1, 0);
Packit 427e91
		}
Packit 427e91
		free(p->tram_lookups);
Packit 427e91
	}
Packit 427e91
	p->tram_lookup_count = count;
Packit 427e91
	p->tram_lookups = tmp;
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_emu_patch_set_delay_count(liblo10k1_emu_patch_t *p, int count)
Packit 427e91
{
Packit 427e91
	liblo10k1_emu_tram_t *tmp = NULL;
Packit 427e91
	int i;
Packit 427e91
	
Packit 427e91
	if (count > 0) {
Packit 427e91
		tmp = (liblo10k1_emu_tram_t *)malloc(sizeof(liblo10k1_emu_tram_t) * count);
Packit 427e91
		if (!tmp)
Packit 427e91
			return LD10K1_ERR_NO_MEM;
Packit 427e91
		memset(tmp, 0, sizeof(liblo10k1_emu_tram_t)*count);
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	if (p->tram_delays) {
Packit 427e91
		for (i = 0; i < p->tram_delay_count; i++) {
Packit 427e91
			liblo10k1_emu_patch_set_line_count(&(p->tram_delays[i]), 0, 0);
Packit 427e91
			liblo10k1_emu_patch_set_line_count(&(p->tram_delays[i]), 1, 0);
Packit 427e91
		}
Packit 427e91
		free(p->tram_delays);
Packit 427e91
	}
Packit 427e91
	p->tram_delay_count = count;
Packit 427e91
	p->tram_delays = tmp;
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_emu_patch_set_instr_count(liblo10k1_emu_patch_t *p, int count)
Packit 427e91
{
Packit 427e91
	liblo10k1_emu_instr_t *tmp = NULL;
Packit 427e91
	
Packit 427e91
	if (count > 0) {
Packit 427e91
		tmp = (liblo10k1_emu_instr_t *)malloc(sizeof(liblo10k1_emu_instr_t) * count);
Packit 427e91
		if (!tmp)
Packit 427e91
			return LD10K1_ERR_NO_MEM;
Packit 427e91
		memset(tmp, 0, sizeof(liblo10k1_emu_instr_t)*count);
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	p->instr_count = count;
Packit 427e91
	if (p->instrs)
Packit 427e91
		free(p->instrs);
Packit 427e91
	p->instrs = tmp;
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
static int read_byte(char *patch_data, int size, int *pos, unsigned char *out)
Packit 427e91
{
Packit 427e91
	if (*pos < size) {
Packit 427e91
		*out = patch_data[*pos];
Packit 427e91
		(*pos)++;
Packit 427e91
		return 0;
Packit 427e91
	} else
Packit 427e91
		return LD10K1_EF_ERR_FORMAT;
Packit 427e91
}
Packit 427e91
Packit 427e91
static int read_ushort(char *patch_data, int size, int *pos, unsigned short *out)
Packit 427e91
{
Packit 427e91
	if (*pos + 1 < size) {
Packit 427e91
		*out = *((unsigned short *)(patch_data + *pos));
Packit 427e91
		*(pos) += 2;
Packit 427e91
		return 0;
Packit 427e91
	} else
Packit 427e91
		return LD10K1_EF_ERR_FORMAT;
Packit 427e91
}
Packit 427e91
Packit 427e91
static int read_uint(char *patch_data, int size, int *pos, unsigned int *out)
Packit 427e91
{
Packit 427e91
	if (*pos + 3 < size) {
Packit 427e91
		*out = *((unsigned int *)(patch_data + *pos));
Packit 427e91
		(*pos) += 4;
Packit 427e91
		return 0;
Packit 427e91
	} else
Packit 427e91
		return LD10K1_EF_ERR_FORMAT;
Packit 427e91
}
Packit 427e91
Packit 427e91
static int read_string(char *patch_data, int size, int *pos, char *out, int ssize)
Packit 427e91
{
Packit 427e91
	if (*pos + ssize - 1 < size) {
Packit 427e91
		strncpy(out, &(patch_data[*pos]), ssize - 1);
Packit 427e91
		out[ssize - 1] = '\0';
Packit 427e91
		(*pos) += ssize;
Packit 427e91
		return 0;
Packit 427e91
	} else
Packit 427e91
		return LD10K1_EF_ERR_FORMAT;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_emu_load_patch(char *file_name, liblo10k1_emu_patch_t **p)
Packit 427e91
{
Packit 427e91
	struct stat patch_stat;
Packit 427e91
	char *patch_data;
Packit 427e91
	FILE *patch_file;
Packit 427e91
	liblo10k1_emu_patch_t *new_patch = NULL;
Packit 427e91
	unsigned int i, j, z, k;
Packit 427e91
	int en = 0;
Packit 427e91
Packit 427e91
	int file_pos = 0;
Packit 427e91
	int file_size = 0;
Packit 427e91
	
Packit 427e91
	unsigned char byte_tmp;
Packit 427e91
	unsigned short ushort_tmp;
Packit 427e91
	
Packit 427e91
	liblo10k1_emu_tram_t *tmp_tram;
Packit 427e91
	liblo10k1_emu_tram_line_t *tmp_tram_lines;
Packit 427e91
	
Packit 427e91
	unsigned int part1, part2;
Packit 427e91
Packit 427e91
	if (!(patch_file = fopen(file_name, "r")))
Packit 427e91
		return LD10K1_EF_ERR_OPEN;
Packit 427e91
Packit 427e91
	/* first load patch to mem */
Packit 427e91
	if (stat(file_name, &patch_stat))
Packit 427e91
		return LD10K1_EF_ERR_STAT;
Packit 427e91
Packit 427e91
	/* minimal patch len is 57 */
Packit 427e91
	if (patch_stat.st_size < 57 || patch_stat.st_size > 1000000)
Packit 427e91
		return LD10K1_EF_ERR_SIZE;
Packit 427e91
Packit 427e91
	file_size = patch_stat.st_size;
Packit 427e91
Packit 427e91
	patch_data = (char *)malloc(patch_stat.st_size);
Packit 427e91
	if (!patch_data)
Packit 427e91
		return LD10K1_ERR_NO_MEM;
Packit 427e91
Packit 427e91
	if (fread(patch_data, patch_stat.st_size, 1, patch_file) != 1) {
Packit 427e91
		fclose(patch_file);
Packit 427e91
		en = LD10K1_EF_ERR_READ;
Packit 427e91
		goto err;
Packit 427e91
	} else
Packit 427e91
		fclose(patch_file);
Packit 427e91
Packit 427e91
	int file_sig = 0;
Packit 427e91
		
Packit 427e91
	/* signature checks - two kinds of as10k1 files, one from alsa-tools, other from emu-tools. */
Packit 427e91
	if(strncmp(patch_data, AS10K1_FILE_SIGNATURE_ALSA, 16) != 0)
Packit 427e91
	{
Packit 427e91
	  if((strncmp(patch_data, AS10K1_FILE_SIGNATURE_EMU, 16) == 0) && (*((unsigned short *)&patch_data[17]) == AS10K1_FILE_FORMAT_VERSION_EMU))
Packit 427e91
	    file_sig = 3;
Packit 427e91
		else	
Packit 427e91
		{
Packit 427e91
	    en = LD10K1_EF_ERR_SIGNATURE;
Packit 427e91
	    goto err;
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	new_patch = liblo10k1_emu_new_patch();
Packit 427e91
	if (!new_patch) {
Packit 427e91
		en = LD10K1_ERR_NO_MEM;
Packit 427e91
		goto err;
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* next patch name */
Packit 427e91
	strncpy(new_patch->patch_name, &(patch_data[16 + file_sig]), 31);
Packit 427e91
	new_patch->patch_name[31] = '\0';
Packit 427e91
	/* registers */
Packit 427e91
	file_pos = 32+16 + file_sig; 
Packit 427e91
	
Packit 427e91
	/* in count */
Packit 427e91
	if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
		  goto err;
Packit 427e91
	
Packit 427e91
	if (byte_tmp >= 32) {
Packit 427e91
		en = LD10K1_EF_ERR_FORMAT;
Packit 427e91
		goto err;
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	if ((en = liblo10k1_emu_patch_set_in_count(new_patch, byte_tmp)) < 0 ||
Packit 427e91
		(en = liblo10k1_emu_patch_set_out_count(new_patch, byte_tmp)) < 0)
Packit 427e91
		goto err;
Packit 427e91
	
Packit 427e91
	/* read in gprs */
Packit 427e91
	for (i = 0; i < new_patch->in_count; i++) {
Packit 427e91
		if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
			goto err;
Packit 427e91
		new_patch->ins[i] = byte_tmp;
Packit 427e91
		if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
			goto err;
Packit 427e91
		new_patch->outs[i] = byte_tmp;
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* read dyn gprs */
Packit 427e91
	if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
		goto err;
Packit 427e91
		
Packit 427e91
	if ((en = liblo10k1_emu_patch_set_dyn_count(new_patch, byte_tmp)) < 0)
Packit 427e91
		goto err;
Packit 427e91
	
Packit 427e91
	for (i = 0; i < new_patch->dyn_count; i++) {
Packit 427e91
		if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
			goto err;
Packit 427e91
		new_patch->dyns[i] = byte_tmp;
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* read sta gprs */
Packit 427e91
	if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
		goto err;
Packit 427e91
		
Packit 427e91
	if ((en = liblo10k1_emu_patch_set_sta_count(new_patch, byte_tmp)) < 0)
Packit 427e91
		goto err;
Packit 427e91
	
Packit 427e91
	for (i = 0; i < new_patch->sta_count; i++) {
Packit 427e91
		if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
			goto err;
Packit 427e91
		new_patch->stas[i].sc = byte_tmp;
Packit 427e91
		if ((en = read_uint(patch_data, file_size, &file_pos, &(new_patch->stas[i].sc_val))) < 0)
Packit 427e91
			goto err;
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* read ctl gprs */
Packit 427e91
	if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
		goto err;
Packit 427e91
		
Packit 427e91
	if ((en = liblo10k1_emu_patch_set_ctl_count(new_patch, byte_tmp)) < 0)
Packit 427e91
		goto err;
Packit 427e91
	
Packit 427e91
	for (i = 0; i < new_patch->ctl_count; i++) {
Packit 427e91
		if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
			goto err;
Packit 427e91
		new_patch->ctls[i].ctl = byte_tmp;
Packit 427e91
		if ((en = read_uint(patch_data, file_size, &file_pos, &(new_patch->ctls[i].ctl_val))) < 0)
Packit 427e91
			goto err;
Packit 427e91
		if ((en = read_uint(patch_data, file_size, &file_pos, &(new_patch->ctls[i].ctl_val_min))) < 0)
Packit 427e91
			goto err;
Packit 427e91
		if ((en = read_uint(patch_data, file_size, &file_pos, &(new_patch->ctls[i].ctl_val_max))) < 0)
Packit 427e91
			goto err;
Packit 427e91
		if ((en = read_string(patch_data, file_size, &file_pos, new_patch->ctls[i].ctl_name, 32)) < 0)
Packit 427e91
			goto err;
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* read const gprs */
Packit 427e91
	if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
		goto err;
Packit 427e91
		
Packit 427e91
	if ((en = liblo10k1_emu_patch_set_con_count(new_patch, byte_tmp)) < 0)
Packit 427e91
		goto err;
Packit 427e91
	
Packit 427e91
	for (i = 0; i < new_patch->con_count; i++) {
Packit 427e91
		if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
			goto err;
Packit 427e91
		new_patch->cons[i].sc = byte_tmp;
Packit 427e91
		if ((en = read_uint(patch_data, file_size, &file_pos, &(new_patch->cons[i].sc_val))) < 0)
Packit 427e91
			goto err;
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* read tram lookup gprs */
Packit 427e91
	for (z = 0; z < 2; z++) {
Packit 427e91
		if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
			goto err;
Packit 427e91
	
Packit 427e91
		if (z) {
Packit 427e91
			if ((en = liblo10k1_emu_patch_set_delay_count(new_patch, byte_tmp)) < 0)
Packit 427e91
				goto err;
Packit 427e91
		} else {		
Packit 427e91
			if ((en = liblo10k1_emu_patch_set_lookup_count(new_patch, byte_tmp)) < 0)
Packit 427e91
				goto err;
Packit 427e91
		}
Packit 427e91
	
Packit 427e91
		for (i = 0; i < (z ? new_patch->tram_delay_count : new_patch->tram_lookup_count); i++) {
Packit 427e91
			/* size */
Packit 427e91
			if (z) {
Packit 427e91
				if ((en = read_uint(patch_data, file_size, &file_pos, &(new_patch->tram_delays[i].size))) < 0)
Packit 427e91
					goto err;
Packit 427e91
				tmp_tram = new_patch->tram_delays + i;
Packit 427e91
			} else {
Packit 427e91
				if ((en = read_uint(patch_data, file_size, &file_pos, &(new_patch->tram_lookups[i].size))) < 0)
Packit 427e91
					goto err;
Packit 427e91
				tmp_tram = new_patch->tram_lookups + i;
Packit 427e91
			}
Packit 427e91
			
Packit 427e91
			for (k = 0; k < 2; k++) {
Packit 427e91
				/* read lines */
Packit 427e91
				if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
					goto err;
Packit 427e91
				
Packit 427e91
				if ((en = liblo10k1_emu_patch_set_line_count(tmp_tram, k, byte_tmp)) < 0)
Packit 427e91
					goto err;
Packit 427e91
				
Packit 427e91
				if (k)
Packit 427e91
					tmp_tram_lines = tmp_tram->write_lines;
Packit 427e91
				else
Packit 427e91
					tmp_tram_lines = tmp_tram->read_lines;
Packit 427e91
				
Packit 427e91
				for (j = 0; j < (k ? tmp_tram->write_line_count : tmp_tram->read_line_count); j++) {
Packit 427e91
					if ((en = read_byte(patch_data, file_size, &file_pos, &byte_tmp)) < 0)
Packit 427e91
						goto err;
Packit 427e91
						
Packit 427e91
					tmp_tram_lines[j].line = byte_tmp;
Packit 427e91
				
Packit 427e91
					if ((en = read_uint(patch_data, file_size, &file_pos, &(tmp_tram_lines[j].line_size))) < 0)
Packit 427e91
						goto err;
Packit 427e91
				}
Packit 427e91
			}
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* instruction lines */
Packit 427e91
	if ((en = read_ushort(patch_data, file_size, &file_pos, &ushort_tmp)) < 0)
Packit 427e91
		goto err;
Packit 427e91
		
Packit 427e91
	if(file_sig)
Packit 427e91
	  ushort_tmp >>= 1;
Packit 427e91
		
Packit 427e91
	if ((en = liblo10k1_emu_patch_set_instr_count(new_patch, ushort_tmp)) < 0)
Packit 427e91
		goto err;
Packit 427e91
	
Packit 427e91
	for (i = 0; i < new_patch->instr_count; i++) {
Packit 427e91
		if ((en = read_uint(patch_data, file_size, &file_pos, &part1)) < 0)
Packit 427e91
			goto err;
Packit 427e91
		if ((en = read_uint(patch_data, file_size, &file_pos, &part2)) < 0)
Packit 427e91
			goto err;
Packit 427e91
			
Packit 427e91
		/* fill instr */
Packit 427e91
		new_patch->instrs[i].arg[2] = part1 >> 10;
Packit 427e91
		new_patch->instrs[i].arg[3] = part1 & 0x3FF;
Packit 427e91
		new_patch->instrs[i].op = part2 >> 20;
Packit 427e91
		new_patch->instrs[i].arg[0] = (part2 >> 10) & 0x3FF;
Packit 427e91
		new_patch->instrs[i].arg[1] = part2 & 0x3FF;
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	*p = new_patch;
Packit 427e91
	
Packit 427e91
	if (patch_data)
Packit 427e91
		free(patch_data);
Packit 427e91
	return 0;
Packit 427e91
err:
Packit 427e91
	if (patch_data)
Packit 427e91
		free(patch_data);
Packit 427e91
	if (new_patch)
Packit 427e91
		liblo10k1_emu_free_patch(new_patch);
Packit 427e91
	return en;
Packit 427e91
}
Packit 427e91
Packit 427e91
typedef struct
Packit 427e91
{
Packit 427e91
	unsigned int gpr;
Packit 427e91
	unsigned int ld_gpr;
Packit 427e91
} used_gpr_t;
Packit 427e91
Packit 427e91
Packit 427e91
static int check_if_used(used_gpr_t *gprs, int count, unsigned int gpr)
Packit 427e91
{
Packit 427e91
	int i;
Packit 427e91
	for (i = 0; i < count; i++) {
Packit 427e91
		if (gprs[i].gpr == gpr)
Packit 427e91
			return i;
Packit 427e91
	}
Packit 427e91
	return -1;
Packit 427e91
}
Packit 427e91
Packit 427e91
static char *default_in_names[] =
Packit 427e91
{
Packit 427e91
	"IL",
Packit 427e91
	"IR",
Packit 427e91
	"IRL",
Packit 427e91
	"IRR",
Packit 427e91
	"IC",
Packit 427e91
	"ILFE"
Packit 427e91
};
Packit 427e91
Packit 427e91
static char *default_out_names[] =
Packit 427e91
{
Packit 427e91
	"OL",
Packit 427e91
	"OR",
Packit 427e91
	"ORL",
Packit 427e91
	"ORR",
Packit 427e91
	"OC",
Packit 427e91
	"OLFE"
Packit 427e91
};
Packit 427e91
Packit 427e91
int liblo10k1_patch_find_ctl_by_name(liblo10k1_dsp_patch_t *p, char *ctl_name)
Packit 427e91
{
Packit 427e91
	int i;
Packit 427e91
	for (i = 0; i < p->ctl_count; i++)
Packit 427e91
		if (strcmp(p->ctl[i].name, ctl_name) == 0)
Packit 427e91
			return i;
Packit 427e91
	return -1;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_patch_ctl_set_trans(liblo10k1_dsp_patch_t *p, int idx, int trans) 
Packit 427e91
{
Packit 427e91
	int i;
Packit 427e91
	switch (trans) {
Packit 427e91
		case EMU10K1_GPR_TRANSLATION_NONE:
Packit 427e91
			break;
Packit 427e91
		case EMU10K1_GPR_TRANSLATION_TABLE100:
Packit 427e91
			if (p->ctl[idx].min != 0 && p->ctl[idx].max != 100)
Packit 427e91
				return LD10K1_EF_ERR_TRANSFORM_TRANS;
Packit 427e91
			break;
Packit 427e91
		case EMU10K1_GPR_TRANSLATION_BASS:
Packit 427e91
		case EMU10K1_GPR_TRANSLATION_TREBLE:
Packit 427e91
			if (p->ctl[idx].min != 0 && p->ctl[idx].max != 0xFFFFFFFF)
Packit 427e91
				return LD10K1_EF_ERR_TRANSFORM_TRANS;
Packit 427e91
			if (p->ctl[idx].count != 5)
Packit 427e91
				return LD10K1_EF_ERR_TRANSFORM_TRANS;
Packit 427e91
			break;
Packit 427e91
		case EMU10K1_GPR_TRANSLATION_ONOFF:
Packit 427e91
			if (p->ctl[idx].min != 0 && p->ctl[idx].max != 1)
Packit 427e91
				return LD10K1_EF_ERR_TRANSFORM_TRANS;
Packit 427e91
			break;
Packit 427e91
	}
Packit 427e91
	for (i = 0; i < p->ctl[idx].count; i++)
Packit 427e91
		if (p->ctl[idx].value[i] < p->ctl[idx].min || p->ctl[idx].value[i] > p->ctl[idx].max)
Packit 427e91
			return LD10K1_EF_ERR_TRANSFORM_TRANS;
Packit 427e91
	p->ctl[idx].translation = trans;
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_patch_ctl_set_vcount(liblo10k1_dsp_patch_t *p, int idx, int vc) 
Packit 427e91
{
Packit 427e91
	if (p->ctl[idx].count < vc)
Packit 427e91
		return LD10K1_EF_ERR_TRANSFORM_CTL;
Packit 427e91
	p->ctl[idx].vcount = vc;
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_patch_ctl_set_index(liblo10k1_dsp_patch_t *p, int idx, int i) 
Packit 427e91
{
Packit 427e91
	p->ctl[idx].index = i;
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_patch_ctl_set_value(liblo10k1_dsp_patch_t *p, int idx, int vi, int val) 
Packit 427e91
{
Packit 427e91
	if (p->ctl[idx].count < vi)
Packit 427e91
		return LD10K1_EF_ERR_TRANSFORM_CTL;
Packit 427e91
	if (val < p->ctl[idx].min || val > p->ctl[idx].max)
Packit 427e91
			return LD10K1_EF_ERR_TRANSFORM_CTL;
Packit 427e91
	p->ctl[idx].value[vi] = val;
Packit 427e91
	return 0;
Packit 427e91
}
Packit 427e91
Packit 427e91
int liblo10k1_emu_transform_patch(liblo10k1_emu_patch_t *ep,  liblo10k1_ctl_transform_t *tctl, int tctl_count, liblo10k1_dsp_patch_t **lp)
Packit 427e91
{
Packit 427e91
	used_gpr_t used_gpr[0x400];
Packit 427e91
	int used_gpr_count = 0;
Packit 427e91
	int i, j, k;
Packit 427e91
	int gpr;
Packit 427e91
	int tmp_cnt;
Packit 427e91
	int idx;
Packit 427e91
	int en = 0;
Packit 427e91
	int io_name_map[6];
Packit 427e91
	int transformed;
Packit 427e91
	liblo10k1_dsp_ctl_t *tmp_nctl;
Packit 427e91
	liblo10k1_emu_ctl_t *tmp_octl;
Packit 427e91
	int const_count, hw_count;	/*int ctl_transform_map[256];*/
Packit 427e91
	liblo10k1_dsp_patch_t *np = NULL;
Packit 427e91
	liblo10k1_emu_tram_t *tram_tmp;
Packit 427e91
	liblo10k1_dsp_tram_acc_t *tram_nacc;
Packit 427e91
	liblo10k1_emu_tram_line_t *tram_line;
Packit 427e91
	int val, addhw, addconst;
Packit 427e91
	
Packit 427e91
	/* for all instruction get used gpr list */
Packit 427e91
	for (i = 0; i < ep->instr_count; i++) {
Packit 427e91
		for (j = 0; j < 4; j++) {
Packit 427e91
			gpr = ep->instrs[i].arg[j];
Packit 427e91
			for (k = 0; k < used_gpr_count; k++)
Packit 427e91
				if (gpr == used_gpr[k].gpr)
Packit 427e91
					break;
Packit 427e91
					
Packit 427e91
			if (k < used_gpr_count)
Packit 427e91
				continue;
Packit 427e91
			
Packit 427e91
			used_gpr[used_gpr_count].gpr = gpr;
Packit 427e91
			used_gpr[used_gpr_count].ld_gpr = 0;
Packit 427e91
			used_gpr_count++;
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	np = liblo10k1_patch_alloc(0, 0, 0, 0, 0, 0, 0, 0, 0, ep->instr_count);
Packit 427e91
	if (!np)
Packit 427e91
		return LD10K1_ERR_NO_MEM;
Packit 427e91
		
Packit 427e91
	/* set patch name */
Packit 427e91
	strcpy(np->patch_name, ep->patch_name);
Packit 427e91
	
Packit 427e91
	/* in gprs */
Packit 427e91
	tmp_cnt = 0;
Packit 427e91
	for (i = 0; i < ep->in_count; i++) {
Packit 427e91
		idx = check_if_used(used_gpr, used_gpr_count, ep->ins[i] + 0x100);
Packit 427e91
		if (idx >= 0) {
Packit 427e91
			used_gpr[idx].ld_gpr = EMU10K1_PREG_IN(tmp_cnt);
Packit 427e91
			if (i < 6)
Packit 427e91
				io_name_map[i] = tmp_cnt;
Packit 427e91
			tmp_cnt++;
Packit 427e91
		} else {
Packit 427e91
			if (i < 6)
Packit 427e91
				io_name_map[i] = -1;
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
		
Packit 427e91
	if ((en = liblo10k1_patch_set_in_count(np, tmp_cnt)) < 0)
Packit 427e91
		goto err;
Packit 427e91
	
Packit 427e91
	/* set in name */
Packit 427e91
	if (ep->in_count == 2 || /* stereo */
Packit 427e91
		ep->in_count == 4 || /* 4 channel */
Packit 427e91
		ep->in_count == 6) { /* 5.1 */
Packit 427e91
		for (i = 0; i < ep->in_count; i++) {
Packit 427e91
			if (io_name_map[i] >= 0)
Packit 427e91
				strcpy(np->ins[io_name_map[i]].name, default_in_names[i]);
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
		
Packit 427e91
	/* out gprs */
Packit 427e91
	tmp_cnt = 0;
Packit 427e91
	for (i = 0; i < ep->out_count; i++) {
Packit 427e91
		idx = check_if_used(used_gpr, used_gpr_count, ep->outs[i] + 0x100);
Packit 427e91
		if (idx >= 0) {
Packit 427e91
			used_gpr[idx].ld_gpr = EMU10K1_PREG_OUT(tmp_cnt);
Packit 427e91
			if (i < 6)
Packit 427e91
				io_name_map[i] = tmp_cnt;
Packit 427e91
			tmp_cnt++;
Packit 427e91
		} else {
Packit 427e91
			if (i < 6)
Packit 427e91
				io_name_map[i] = -1;
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
		
Packit 427e91
	if ((en = liblo10k1_patch_set_out_count(np, tmp_cnt)) < 0)
Packit 427e91
		goto err;
Packit 427e91
	
Packit 427e91
	/* set out name */
Packit 427e91
	if (ep->out_count == 2 || /* stereo */
Packit 427e91
		ep->out_count == 4 || /* 4 channel */
Packit 427e91
		ep->out_count == 6) { /* 5.1 */
Packit 427e91
		for (i = 0; i < ep->out_count; i++) {
Packit 427e91
			if (io_name_map[i] >= 0)
Packit 427e91
				strcpy(np->outs[io_name_map[i]].name, default_out_names[i]);
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* dyn regs */
Packit 427e91
	tmp_cnt = 0;
Packit 427e91
	for (i = 0; i < ep->dyn_count; i++) {
Packit 427e91
		idx = check_if_used(used_gpr, used_gpr_count, ep->dyns[i] + 0x100);
Packit 427e91
		if (idx >= 0) {
Packit 427e91
			used_gpr[idx].ld_gpr = EMU10K1_PREG_DYN(tmp_cnt);
Packit 427e91
			tmp_cnt++;
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	if ((en = liblo10k1_patch_set_dyn_count(np, tmp_cnt)) < 0)
Packit 427e91
		goto err;
Packit 427e91
	
Packit 427e91
	/* sta regs */
Packit 427e91
	tmp_cnt = 0;
Packit 427e91
	for (i = 0; i < ep->sta_count; i++) {
Packit 427e91
		idx = check_if_used(used_gpr, used_gpr_count, ep->stas[i].sc + 0x100);
Packit 427e91
		if (idx >= 0) {
Packit 427e91
			used_gpr[idx].ld_gpr = EMU10K1_PREG_STA(tmp_cnt);
Packit 427e91
			tmp_cnt++;
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	if ((en = liblo10k1_patch_set_sta_count(np, tmp_cnt)) < 0)
Packit 427e91
		goto err;
Packit 427e91
		
Packit 427e91
	/* sta regs - initilization */
Packit 427e91
	tmp_cnt = 0;
Packit 427e91
	for (i = 0; i < ep->sta_count; i++) {
Packit 427e91
		idx = check_if_used(used_gpr, used_gpr_count, ep->stas[i].sc + 0x100);
Packit 427e91
		if (idx >= 0) {
Packit 427e91
			np->stas[tmp_cnt].const_val = ep->stas[i].sc_val;
Packit 427e91
			tmp_cnt++;
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* FIXME - ak je niektoty ctl pouzity v tctl viackrat tak to zblbne */
Packit 427e91
	/* ctls regs */
Packit 427e91
	/* first get count of ctls */
Packit 427e91
	tmp_cnt = 0;
Packit 427e91
	for (i = 0; i < tctl_count; i++)
Packit 427e91
		tmp_cnt += tctl[i].emu_ctl_count;
Packit 427e91
	
Packit 427e91
	if ((en = liblo10k1_patch_set_ctl_count(np, ep->ctl_count - tmp_cnt + tctl_count)) < 0)
Packit 427e91
		goto err;
Packit 427e91
		
Packit 427e91
	tmp_cnt = 0;
Packit 427e91
	for (i = 0; i < ep->ctl_count; i++) {
Packit 427e91
		tmp_octl = &(ep->ctls[i]);
Packit 427e91
		/* find if transformed */
Packit 427e91
		transformed = 0;
Packit 427e91
		for (j = 0; j < tctl_count; j++) {
Packit 427e91
			for (k = 0; k < tctl[j].emu_ctl_count; k++) {
Packit 427e91
				if (i == tctl[j].emu_ctls[k]) {
Packit 427e91
					/* it is transformed */
Packit 427e91
					tmp_nctl = &(np->ctl[j]);
Packit 427e91
					if (strcmp(tmp_nctl->name, "") != 0) {
Packit 427e91
						/* initialized - check min, max */
Packit 427e91
						if (tmp_octl->ctl_val_min != tmp_nctl->min ||
Packit 427e91
							tmp_octl->ctl_val_max != tmp_nctl->max) {
Packit 427e91
							en = LD10K1_EF_ERR_TRANSFORM_CTL;
Packit 427e91
							goto err;
Packit 427e91
						}
Packit 427e91
						
Packit 427e91
						tmp_nctl->value[k] = tmp_octl->ctl_val;
Packit 427e91
					} else {
Packit 427e91
						/* initialize it */
Packit 427e91
						strcpy(tmp_nctl->name, tctl[j].ctl_name);
Packit 427e91
						tmp_nctl->index = -1;
Packit 427e91
						tmp_nctl->vcount = tctl[j].emu_ctl_count;/*1;*/
Packit 427e91
						tmp_nctl->count = tctl[j].emu_ctl_count;/*1;*/
Packit 427e91
						tmp_nctl->value[k] = tmp_octl->ctl_val;
Packit 427e91
						tmp_nctl->min = tmp_octl->ctl_val_min;
Packit 427e91
						tmp_nctl->max = tmp_octl->ctl_val_max;
Packit 427e91
						tmp_nctl->translation = EMU10K1_GPR_TRANSLATION_NONE;
Packit 427e91
					}
Packit 427e91
					
Packit 427e91
					idx = check_if_used(used_gpr, used_gpr_count, tmp_octl->ctl + 0x100);
Packit 427e91
					if (idx >= 0)
Packit 427e91
						used_gpr[idx].ld_gpr = EMU10K1_PREG_CTL(j, k);
Packit 427e91
					
Packit 427e91
					transformed = 1;
Packit 427e91
					break;
Packit 427e91
				}
Packit 427e91
			}
Packit 427e91
			if (transformed)
Packit 427e91
				break;
Packit 427e91
		}
Packit 427e91
		
Packit 427e91
		if (transformed)
Packit 427e91
			continue;
Packit 427e91
		/* not transformed */
Packit 427e91
		tmp_nctl = &(np->ctl[tmp_cnt + tctl_count]);
Packit 427e91
		
Packit 427e91
		strcpy(tmp_nctl->name, tmp_octl->ctl_name);
Packit 427e91
		tmp_nctl->index = -1;
Packit 427e91
		tmp_nctl->vcount = 1;
Packit 427e91
		tmp_nctl->count = 1;
Packit 427e91
		tmp_nctl->value[0] = tmp_octl->ctl_val;
Packit 427e91
		tmp_nctl->min = tmp_octl->ctl_val_min;
Packit 427e91
		tmp_nctl->max = tmp_octl->ctl_val_max;
Packit 427e91
		tmp_nctl->translation = EMU10K1_GPR_TRANSLATION_NONE;
Packit 427e91
Packit 427e91
		idx = check_if_used(used_gpr, used_gpr_count, tmp_octl->ctl + 0x100);
Packit 427e91
		if (idx >= 0)
Packit 427e91
			used_gpr[idx].ld_gpr = EMU10K1_PREG_CTL(tmp_cnt + tctl_count, 0);
Packit 427e91
		
Packit 427e91
		tmp_cnt++;
Packit 427e91
		
Packit 427e91
		if (tmp_cnt > np->ctl_count) {
Packit 427e91
			en = LD10K1_EF_ERR_TRANSFORM_CTL;
Packit 427e91
			goto err;
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	if (tmp_cnt + tctl_count < np->ctl_count) {
Packit 427e91
		en = LD10K1_EF_ERR_TRANSFORM_CTL;
Packit 427e91
		goto err;
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* tram */
Packit 427e91
	if ((en = liblo10k1_patch_set_tram_count(np, ep->tram_lookup_count + ep->tram_delay_count)) < 0)
Packit 427e91
		goto err;
Packit 427e91
	
Packit 427e91
	tmp_cnt = 0;
Packit 427e91
	for (i = 0; i < ep->tram_lookup_count + ep->tram_delay_count; i++) {
Packit 427e91
		if (i < ep->tram_lookup_count)
Packit 427e91
			tram_tmp = &(ep->tram_lookups[i]);
Packit 427e91
		else
Packit 427e91
			tram_tmp = &(ep->tram_delays[i - ep->tram_lookup_count]);
Packit 427e91
			
Packit 427e91
		tmp_cnt += tram_tmp->read_line_count + tram_tmp->write_line_count;
Packit 427e91
		np->tram[i].grp_type = i < ep->tram_lookup_count ? TRAM_GRP_TABLE : TRAM_GRP_DELAY;
Packit 427e91
		np->tram[i].grp_size = tram_tmp->size;
Packit 427e91
		np->tram[i].grp_pos = TRAM_POS_AUTO;
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* tram acc */
Packit 427e91
	if ((en = liblo10k1_patch_set_tram_acc_count(np, tmp_cnt)) < 0)
Packit 427e91
		goto err;
Packit 427e91
		
Packit 427e91
	tmp_cnt = 0;
Packit 427e91
	for (i = 0; i < ep->tram_lookup_count + ep->tram_delay_count; i++) {
Packit 427e91
		if (i < ep->tram_lookup_count)
Packit 427e91
			tram_tmp = &(ep->tram_lookups[i]);
Packit 427e91
		else
Packit 427e91
			tram_tmp = &(ep->tram_delays[i - ep->tram_lookup_count]);
Packit 427e91
			
Packit 427e91
		for (k = 0; k < 2; k++) {
Packit 427e91
			for (j = 0; j < (k ? tram_tmp->write_line_count : tram_tmp->read_line_count); j++) {
Packit 427e91
				if (k)
Packit 427e91
					tram_line = &(tram_tmp->write_lines[j]);
Packit 427e91
				else
Packit 427e91
					tram_line = &(tram_tmp->read_lines[j]);
Packit 427e91
					
Packit 427e91
				tram_nacc = &(np->tram_acc[tmp_cnt]);
Packit 427e91
					
Packit 427e91
				tram_nacc->grp = i;
Packit 427e91
				tram_nacc->acc_offset = tram_line->line_size;
Packit 427e91
				tram_nacc->acc_type = k ? TRAM_ACC_WRITE : TRAM_ACC_READ;
Packit 427e91
				
Packit 427e91
				idx = check_if_used(used_gpr, used_gpr_count, tram_line->line + 0x200);
Packit 427e91
				if (idx >= 0)
Packit 427e91
					used_gpr[idx].ld_gpr = EMU10K1_PREG_TRAM_DATA(tmp_cnt);
Packit 427e91
				
Packit 427e91
				idx = check_if_used(used_gpr, used_gpr_count, tram_line->line + 0x300);
Packit 427e91
				if (idx >= 0)
Packit 427e91
					used_gpr[idx].ld_gpr = EMU10K1_PREG_TRAM_ADDR(tmp_cnt);
Packit 427e91
			
Packit 427e91
				tmp_cnt++;
Packit 427e91
			}
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* const and hw */
Packit 427e91
	const_count = 0;
Packit 427e91
	hw_count = 0;
Packit 427e91
	
Packit 427e91
	for (i = 0; i < used_gpr_count; i++) {
Packit 427e91
		gpr = used_gpr[i].gpr;
Packit 427e91
		
Packit 427e91
		if (gpr < 0x40)
Packit 427e91
			hw_count++;
Packit 427e91
		else if (gpr < 0x56)
Packit 427e91
			const_count++;
Packit 427e91
		else if (gpr < 0x5C)
Packit 427e91
			hw_count++;
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* const regs */
Packit 427e91
	tmp_cnt = 0;
Packit 427e91
	for (i = 0; i < ep->con_count; i++) {
Packit 427e91
		idx = check_if_used(used_gpr, used_gpr_count, ep->cons[i].sc + 0x100);
Packit 427e91
		if (idx >= 0) {
Packit 427e91
			used_gpr[idx].ld_gpr = EMU10K1_PREG_CONST(tmp_cnt);
Packit 427e91
			tmp_cnt++;
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* consts */
Packit 427e91
	if ((en = liblo10k1_patch_set_const_count(np, const_count + tmp_cnt)) < 0)
Packit 427e91
		goto err;
Packit 427e91
		
Packit 427e91
	const_count = tmp_cnt;
Packit 427e91
	
Packit 427e91
	/* const regs - initilization */
Packit 427e91
	tmp_cnt = 0;
Packit 427e91
	for (i = 0; i < ep->con_count; i++) {
Packit 427e91
		idx = check_if_used(used_gpr, used_gpr_count, ep->cons[i].sc + 0x100);
Packit 427e91
		if (idx >= 0) {
Packit 427e91
			np->consts[tmp_cnt].const_val = ep->cons[i].sc_val;
Packit 427e91
			tmp_cnt++;
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	/* hw */
Packit 427e91
	if ((en = liblo10k1_patch_set_hw_count(np, hw_count)) < 0)
Packit 427e91
		goto err;
Packit 427e91
		
Packit 427e91
	hw_count = 0;
Packit 427e91
	for (i = 0; i < used_gpr_count; i++) {
Packit 427e91
		gpr = used_gpr[i].gpr;
Packit 427e91
		addconst = 0;
Packit 427e91
		addhw = 0;		
Packit 427e91
		
Packit 427e91
		if (gpr < 0x40) {
Packit 427e91
			/* fx */
Packit 427e91
			addhw = 1;
Packit 427e91
			if (gpr < 0x10)
Packit 427e91
				val = EMU10K1_REG_FX(gpr);
Packit 427e91
			else if (gpr < 0x20)
Packit 427e91
				val = EMU10K1_REG_IN(gpr - 0x10);
Packit 427e91
			else
Packit 427e91
				val = EMU10K1_REG_OUT(gpr - 0x20);
Packit 427e91
		} else {
Packit 427e91
			switch (gpr) {
Packit 427e91
				case 0x40:
Packit 427e91
					addconst = 1; val = 0x00000000;
Packit 427e91
					break;
Packit 427e91
				case 0x41:
Packit 427e91
					addconst = 1; val = 0x00000001;
Packit 427e91
					break;
Packit 427e91
				case 0x42:
Packit 427e91
					addconst = 1; val = 0x00000002;
Packit 427e91
					break;
Packit 427e91
				case 0x43:
Packit 427e91
					addconst = 1; val = 0x00000003;
Packit 427e91
					break;
Packit 427e91
				case 0x44:
Packit 427e91
					addconst = 1; val = 0x00000004;
Packit 427e91
					break;
Packit 427e91
				case 0x45:
Packit 427e91
					addconst = 1; val = 0x00000008;
Packit 427e91
					break;
Packit 427e91
				case 0x46:
Packit 427e91
					addconst = 1; val = 0x00000010;
Packit 427e91
					break;
Packit 427e91
				case 0x47:
Packit 427e91
					addconst = 1; val = 0x00000020;
Packit 427e91
					break;
Packit 427e91
				case 0x48:
Packit 427e91
					addconst = 1; val = 0x00000100;
Packit 427e91
					break;
Packit 427e91
				case 0x49:
Packit 427e91
					addconst = 1; val = 0x00010000;
Packit 427e91
					break;
Packit 427e91
				case 0x4A:
Packit 427e91
					addconst = 1; val = 0x00080000;
Packit 427e91
					break;
Packit 427e91
				case 0x4B:
Packit 427e91
					addconst = 1; val = 0x10000000;
Packit 427e91
					break;
Packit 427e91
				case 0x4C:
Packit 427e91
					addconst = 1; val = 0x20000000;
Packit 427e91
					break;
Packit 427e91
				case 0x4D:
Packit 427e91
					addconst = 1; val = 0x40000000;
Packit 427e91
					break;
Packit 427e91
				case 0x4E:
Packit 427e91
					addconst = 1; val = 0x80000000;
Packit 427e91
					break;
Packit 427e91
				case 0x4F:
Packit 427e91
					addconst = 1; val = 0x7FFFFFFF;
Packit 427e91
					break;
Packit 427e91
				case 0x50:
Packit 427e91
					addconst = 1; val = 0xFFFFFFFF;
Packit 427e91
					break;
Packit 427e91
				case 0x51:
Packit 427e91
					addconst = 1; val = 0xFFFFFFFE;
Packit 427e91
					break;
Packit 427e91
				case 0x52:
Packit 427e91
					addconst = 1; val = 0xC0000000;
Packit 427e91
					break;
Packit 427e91
				case 0x53:
Packit 427e91
					addconst = 1; val = 0x4F1BBCDC;
Packit 427e91
					break;
Packit 427e91
				case 0x54:
Packit 427e91
					addconst = 1; val = 0x5A7EF9DB;
Packit 427e91
					break;
Packit 427e91
				case 0x55:
Packit 427e91
					addconst = 1; val = 0x00100000;
Packit 427e91
					break;
Packit 427e91
				case 0x56:
Packit 427e91
					addhw = 1; val = EMU10K1_NREG_HW_ACCUM;
Packit 427e91
					break;
Packit 427e91
				case 0x57:
Packit 427e91
					addhw = 1; val = EMU10K1_NREG_HW_CCR;
Packit 427e91
					break;
Packit 427e91
				case 0x58:
Packit 427e91
					addhw = 1; val = EMU10K1_NREG_HW_NOISE1;
Packit 427e91
					break;
Packit 427e91
				case 0x59:
Packit 427e91
					addhw = 1; val = EMU10K1_NREG_HW_NOISE2;
Packit 427e91
					break;
Packit 427e91
				case 0x5A:
Packit 427e91
					addhw = 1; val = EMU10K1_NREG_HW_IRQ;
Packit 427e91
					break;
Packit 427e91
				case 0x5B:
Packit 427e91
					addhw = 1; val = EMU10K1_NREG_HW_DBAC;
Packit 427e91
					break;
Packit 427e91
				default:
Packit 427e91
					if (gpr < 0x100) {
Packit 427e91
						en = LD10K1_EF_ERR_TRANSFORM;
Packit 427e91
						goto err;
Packit 427e91
					}
Packit 427e91
					break;
Packit 427e91
			}
Packit 427e91
		}
Packit 427e91
		
Packit 427e91
		if (addhw) {
Packit 427e91
			np->hws[hw_count].hw_val = val;
Packit 427e91
			used_gpr[i].ld_gpr = EMU10K1_PREG_HW(hw_count);
Packit 427e91
			hw_count++;
Packit 427e91
		} else if (addconst) {
Packit 427e91
			np->consts[const_count].const_val = val;
Packit 427e91
			used_gpr[i].ld_gpr = EMU10K1_PREG_CONST(const_count);
Packit 427e91
			const_count++;
Packit 427e91
		}	
Packit 427e91
	}	
Packit 427e91
Packit 427e91
	/* instrs */
Packit 427e91
	if ((en = liblo10k1_patch_set_instr_count(np, ep->instr_count)) < 0)
Packit 427e91
		goto err;
Packit 427e91
	
Packit 427e91
	for (i = 0; i < ep->instr_count; i++) {
Packit 427e91
		np->instr[i].op_code = ep->instrs[i].op;
Packit 427e91
		for (j = 0; j < 4; j++) {
Packit 427e91
			gpr = ep->instrs[i].arg[j];
Packit 427e91
			
Packit 427e91
			idx = check_if_used(used_gpr, used_gpr_count, gpr);
Packit 427e91
			if (!used_gpr[idx].ld_gpr) {
Packit 427e91
				en = LD10K1_EF_ERR_TRANSFORM;
Packit 427e91
				goto err;
Packit 427e91
			}
Packit 427e91
				
Packit 427e91
			np->instr[i].arg[j] = used_gpr[idx].ld_gpr;
Packit 427e91
		}
Packit 427e91
	}
Packit 427e91
	
Packit 427e91
	*lp = np;
Packit 427e91
	return 0;
Packit 427e91
err:
Packit 427e91
	if (np)
Packit 427e91
		liblo10k1_patch_free(np);
Packit 427e91
	return en;
Packit 427e91
}
Packit 427e91