73de812cb6
git-svn-id: svn://svn.rockbox.org/rockbox/trunk@16226 a1c6a512-1295-4272-9138-f99709370657
135 lines
3.4 KiB
C
135 lines
3.4 KiB
C
/***************************************************************************
|
|
* __________ __ ___.
|
|
* Open \______ \ ____ ____ | | _\_ |__ _______ ___
|
|
* Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
|
|
* Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
|
|
* Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
|
|
* \/ \/ \/ \/ \/
|
|
* $Id$
|
|
*
|
|
* Copyright (C) 2007 by Will Robertson
|
|
*
|
|
* All files in this archive are subject to the GNU General Public License.
|
|
* See the file COPYING in the source tree root for full license agreement.
|
|
*
|
|
* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
|
|
* KIND, either express or implied.
|
|
*
|
|
****************************************************************************/
|
|
#include "config.h"
|
|
#include "cpu.h"
|
|
#include "kernel.h"
|
|
#include "thread.h"
|
|
#include "system.h"
|
|
#include "power.h"
|
|
#include "panic.h"
|
|
#include "pcf50606.h"
|
|
#include "ata-target.h"
|
|
|
|
#define ATA_RST (1 << 6)
|
|
|
|
void ata_reset(void)
|
|
{
|
|
ATA_CONTROL &= ~ATA_RST;
|
|
sleep(1);
|
|
ATA_CONTROL |= ATA_RST;
|
|
sleep(1);
|
|
}
|
|
|
|
/* This function is called before enabling the USB bus */
|
|
void ata_enable(bool on)
|
|
{
|
|
(void)on;
|
|
}
|
|
|
|
bool ata_is_coldstart(void)
|
|
{
|
|
return true;
|
|
}
|
|
|
|
unsigned long get_pll(bool serial) {
|
|
unsigned long mfi, mfn, mfd, pdf, ref_clk;
|
|
unsigned long reg = 0, ccmr;
|
|
unsigned long long temp;
|
|
unsigned int prcs;
|
|
|
|
ccmr = CLKCTL_CCMR;
|
|
prcs = (ccmr & 0x6) >> 1;
|
|
if(prcs == 0x1) {
|
|
ref_clk = 32768 * 1024;
|
|
} else {
|
|
ref_clk = 27000000;
|
|
}
|
|
|
|
if(serial) {
|
|
reg = CLKCTL_SPCTL;
|
|
} else {
|
|
if((ccmr & 0x8) == 0)
|
|
return ref_clk;
|
|
if((ccmr & 0x80) != 0)
|
|
return ref_clk;
|
|
reg = CLKCTL_MPCTL;
|
|
}
|
|
pdf = (reg & (0x7 << 26)) >> 26;
|
|
mfd = (reg & (0x3FF << 16)) >> 16;
|
|
mfi = (reg & (0xF << 10)) >> 10;
|
|
mfi = (mfi <= 5) ? 5 : mfi;
|
|
mfn = (reg & 0x3FF);
|
|
|
|
if(mfn < 0x200) {
|
|
temp = (unsigned long long)2 *ref_clk * mfn;
|
|
temp /= (mfd + 1);
|
|
temp = (unsigned long long)2 *ref_clk * mfi + temp;
|
|
temp /= (pdf + 1);
|
|
} else {
|
|
temp = (unsigned long long)2 *ref_clk * (0x400 - mfn);
|
|
temp /= (mfd + 1);
|
|
temp = (unsigned long long)2 *ref_clk * mfi - temp;
|
|
temp /= (pdf + 1);
|
|
|
|
}
|
|
return (unsigned long)temp;
|
|
}
|
|
|
|
unsigned long get_ata_clock(void) {
|
|
unsigned long pll, ret_val, hclk, max_pdf, ipg_pdf, mcu_pdf;
|
|
|
|
max_pdf = (CLKCTL_PDR0 & (0x7 << 3)) >> 3;
|
|
ipg_pdf = (CLKCTL_PDR0 & (0x3 << 6)) >> 6;
|
|
mcu_pdf = (CLKCTL_PDR0 & 0x7);
|
|
if((CLKCTL_PMCR0 & 0xC0000000 ) == 0) {
|
|
pll = get_pll(true);
|
|
} else {
|
|
pll = get_pll(false);
|
|
}
|
|
hclk = pll/(max_pdf + 1);
|
|
ret_val = hclk / (ipg_pdf + 1);
|
|
|
|
return ret_val;
|
|
}
|
|
|
|
void ata_device_init(void)
|
|
{
|
|
ATA_CONTROL |= ATA_RST; /* Make sure we're not in reset mode */
|
|
|
|
/* Setup the timing for PIO mode */
|
|
int T = 1000 * 1000 * 1000 / get_ata_clock();
|
|
TIME_OFF = 3;
|
|
TIME_ON = 3;
|
|
|
|
TIME_1 = (T + 70)/T;
|
|
TIME_2W = (T + 290)/T;
|
|
TIME_2R = (T + 290)/T;
|
|
TIME_AX = (T + 50)/T;
|
|
TIME_PIO_RDX = 1;
|
|
TIME_4 = (T + 30)/T;
|
|
TIME_9 = (T + 20)/T;
|
|
}
|
|
|
|
#if !defined(BOOTLOADER)
|
|
void copy_read_sectors(unsigned char* buf, int wordcount)
|
|
{
|
|
(void)buf;
|
|
(void)wordcount;
|
|
}
|
|
#endif
|