oh, hello bluetooth dongle :D
[ppcskel.git] / mini_ipc.c
1 /*
2         mini_ipc.c -- public PowerPC-side interface to mini.  Part of the
3         BootMii project.
4
5 Copyright (C) 2009                      Andre Heider "dhewg" <dhewg@wiibrew.org>
6 Copyright (C) 2009                      Haxx Enterprises <bushing@gmail.com>
7 Copyright (C) 2009                      John Kelley <wiidev@kelley.ca>
8 Copyright (C) 2008, 2009        Sven Peter <svenpeter@gmail.com>
9
10 # This code is licensed to you under the terms of the GNU GPL, version 2;
11 # see file COPYING or http://www.gnu.org/licenses/old-licenses/gpl-2.0.txt
12 */
13
14 #include "bootmii_ppc.h"
15 #include "ipc.h"
16 #include "mini_ipc.h"
17 #include "string.h"
18
19 int ipc_powerpc_boot(const void *addr, u32 len)
20 {
21         ipc_request *req;
22
23         sync_after_write(addr, len);
24         req =  ipc_exchange(IPC_PPC_BOOT, 3, 0, virt_to_phys(addr), len);
25         return req->args[0];
26 }
27
28 u32 boot2_run(u32 hi, u32 lo)
29 {
30         ipc_request * req;
31         req =  ipc_exchange(IPC_BOOT2_RUN, 2, hi, lo);
32         return req->args[0];
33 }
34
35 tmd *boot2_tmd(void)
36 {
37         tmd *ret = phys_to_virt(ipc_exchange(IPC_BOOT2_TMD, 0)->args[0]);
38         sync_before_read(ret, sizeof(tmd));
39         return ret;
40 }
41
42 void getotp(otp_t *otp)
43 {
44         sync_before_read(otp, sizeof(*otp));
45         ipc_exchange(IPC_KEYS_GETOTP, 1, virt_to_phys(otp));
46 }
47
48 void getMiniGitVer(char *buf, u16 len)
49 {
50         if (len < 32)
51         {
52                 memset((void *)buf, 0, 32);
53                 return;
54         }
55         sync_before_read(buf, len);
56         ipc_exchange(IPC_SYS_GETGITS, 1, virt_to_phys(buf));
57 }
58
59 void getseeprom(seeprom_t *seeprom)
60 {
61         sync_before_read(seeprom, sizeof(*seeprom));
62         ipc_exchange(IPC_KEYS_GETEEP, 1, virt_to_phys(seeprom));
63 }
64
65 void aes_reset(void)
66 {
67         ipc_exchange(IPC_AES_RESET, 0);
68 }
69
70 void aes_set_key(u8 *key)
71 {
72         u32 *keyptr = (u32 *)key;
73         ipc_exchange(IPC_AES_SETKEY, 4, keyptr[0], keyptr[1], keyptr[2], keyptr[3]);
74 }
75
76 void aes_set_iv(u8 *iv)
77 {
78         u32 *ivptr = (u32 *)iv;
79         ipc_exchange(IPC_AES_SETIV, 4, ivptr[0], ivptr[1], ivptr[2], ivptr[3]);
80 }
81
82 void aes_decrypt(u8 *src, u8 *dst, u32 blocks, u8 keep_iv)
83 {
84         sync_after_write(src, (blocks+1)*16);
85         ipc_exchange(IPC_AES_DECRYPT, 4, virt_to_phys(src), virt_to_phys(dst), blocks, keep_iv);
86         sync_before_read(dst, (blocks+1)*16);
87 }
88
89 void nand_reset(void)
90 {
91         ipc_exchange(IPC_NAND_RESET, 0);
92 }
93
94 u32 nand_getid(void)
95 {
96         static u8 idbuf[64] __attribute__((aligned(64)));
97
98         ipc_exchange(IPC_NAND_GETID, 1, virt_to_phys(&idbuf));
99         sync_before_read(idbuf, 0x40);
100
101         return idbuf[0] << 24 | idbuf[1] << 16 | idbuf[2] << 8 | idbuf[3];
102 }
103
104 u8 nand_status(void)
105 {
106         static u8 buf[64] __attribute__((aligned(64)));
107
108         ipc_exchange(IPC_NAND_STATUS, 1, virt_to_phys(&buf));
109         sync_before_read(buf, 0x40);
110
111         return buf[0];
112 }
113
114 int nand_read(u32 pageno, void *data, void *ecc)
115 {
116         if (data)
117                 sync_before_read(data, 0x800);
118         if (ecc)
119                 sync_before_read(ecc, 0x40);
120         return ipc_exchange(IPC_NAND_READ, 3, pageno,
121                 (!data ? (u32)-1 : virt_to_phys(data)),
122                 (!ecc ? (u32)-1 : virt_to_phys(ecc)))->args[0];
123 }
124
125 void nand_write(u32 pageno, void *data, void *ecc)
126 {
127         if (data)
128                 sync_after_write(data, 0x800);
129         if (ecc)
130                 sync_after_write(ecc, 0x40);
131         ipc_exchange(IPC_NAND_WRITE, 3, pageno,
132                 (!data ? (u32)-1 : virt_to_phys(data)),
133                 (!ecc ? (u32)-1 : virt_to_phys(ecc)));
134 }
135
136 void nand_erase(u32 pageno)
137 {
138         ipc_exchange(IPC_NAND_ERASE, 1, pageno);
139 }
140
141 int sd_mount(void)
142 {
143         return ipc_exchange(IPC_SDMMC_ACK, 0)->args[0];
144 }
145
146 int sd_get_state(void)
147 {
148         return ipc_exchange(IPC_SDMMC_STATE, 0)->args[0];
149 }
150
151 int sd_protected(void)
152 {
153 //      return (ipc_exchange(IPC_SD_GETSTATE, 0)->args[0] & SDHC_WRITE_PROTECT) == SDHC_WRITE_PROTECT;
154         return 0;
155 }
156
157 int sd_select(void)
158 {
159         return 1;
160 //      return ipc_exchange(IPC_SD_SELECT, 0)->args[0];
161 }
162
163 int sd_read(u32 start_block, u32 blk_cnt, void *buffer)
164 {
165         int retval;
166         sync_before_read(buffer, blk_cnt * 512);
167         retval = ipc_exchange(IPC_SDMMC_READ, 3, start_block, blk_cnt, virt_to_phys(buffer))->args[0];
168         return retval;
169 }
170
171 int sd_write(u32 start_block, u32 blk_cnt, const void *buffer)
172 {
173         int retval;
174         sync_after_write(buffer, blk_cnt * 512);
175         retval = ipc_exchange(IPC_SDMMC_WRITE, 3, start_block, blk_cnt, virt_to_phys(buffer))->args[0];
176
177         return retval;
178 }
179
180 u32 sd_getsize(void)
181 {
182         return ipc_exchange(IPC_SDMMC_SIZE, 0)->args[0];
183 }
184