1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
|
/*
* mostek.h: Describes the various Mostek time of day clock registers.
*
* Copyright (C) 1995 David S. Miller (davem@caip.rutgers.edu)
* Copyright (C) 1996 Thomas K. Dyas (tdyas@eden.rutgers.edu)
* Added intersil code 05/25/98 Chris Davis (cdavis@cois.on.ca)
*/
#ifndef _SPARC_MOSTEK_H
#define _SPARC_MOSTEK_H
#include <asm/idprom.h>
#include <asm/io.h>
/* M48T02 Register Map (adapted from Sun NVRAM/Hostid FAQ)
*
* Data
* Address Function
* Bit 7 Bit 6 Bit 5 Bit 4Bit 3 Bit 2 Bit 1 Bit 0
* 7ff - - - - - - - - Year 00-99
* 7fe 0 0 0 - - - - - Month 01-12
* 7fd 0 0 - - - - - - Date 01-31
* 7fc 0 FT 0 0 0 - - - Day 01-07
* 7fb KS 0 - - - - - - Hours 00-23
* 7fa 0 - - - - - - - Minutes 00-59
* 7f9 ST - - - - - - - Seconds 00-59
* 7f8 W R S - - - - - Control
*
* * ST is STOP BIT
* * W is WRITE BIT
* * R is READ BIT
* * S is SIGN BIT
* * FT is FREQ TEST BIT
* * KS is KICK START BIT
*/
/* The Mostek 48t02 real time clock and NVRAM chip. The registers
* other than the control register are in binary coded decimal. Some
* control bits also live outside the control register.
*/
#define mostek_read(_addr) readb(_addr)
#define mostek_write(_addr,_val) writeb(_val, _addr)
#define MOSTEK_EEPROM 0x0000UL
#define MOSTEK_IDPROM 0x07d8UL
#define MOSTEK_CREG 0x07f8UL
#define MOSTEK_SEC 0x07f9UL
#define MOSTEK_MIN 0x07faUL
#define MOSTEK_HOUR 0x07fbUL
#define MOSTEK_DOW 0x07fcUL
#define MOSTEK_DOM 0x07fdUL
#define MOSTEK_MONTH 0x07feUL
#define MOSTEK_YEAR 0x07ffUL
struct mostek48t02 {
volatile char eeprom[2008]; /* This is the eeprom, don't touch! */
struct idprom idprom; /* The idprom lives here. */
volatile unsigned char creg; /* Control register */
volatile unsigned char sec; /* Seconds (0-59) */
volatile unsigned char min; /* Minutes (0-59) */
volatile unsigned char hour; /* Hour (0-23) */
volatile unsigned char dow; /* Day of the week (1-7) */
volatile unsigned char dom; /* Day of the month (1-31) */
volatile unsigned char month; /* Month of year (1-12) */
volatile unsigned char year; /* Year (0-99) */
};
extern spinlock_t mostek_lock;
extern void __iomem *mstk48t02_regs;
/* Control register values. */
#define MSTK_CREG_WRITE 0x80 /* Must set this before placing values. */
#define MSTK_CREG_READ 0x40 /* Stop updates to allow a clean read. */
#define MSTK_CREG_SIGN 0x20 /* Slow/speed clock in calibration mode. */
/* Control bits that live in the other registers. */
#define MSTK_STOP 0x80 /* Stop the clock oscillator. (sec) */
#define MSTK_KICK_START 0x80 /* Kick start the clock chip. (hour) */
#define MSTK_FREQ_TEST 0x40 /* Frequency test mode. (day) */
#define MSTK_YEAR_ZERO 1968 /* If year reg has zero, it is 1968. */
#define MSTK_CVT_YEAR(yr) ((yr) + MSTK_YEAR_ZERO)
/* Masks that define how much space each value takes up. */
#define MSTK_SEC_MASK 0x7f
#define MSTK_MIN_MASK 0x7f
#define MSTK_HOUR_MASK 0x3f
#define MSTK_DOW_MASK 0x07
#define MSTK_DOM_MASK 0x3f
#define MSTK_MONTH_MASK 0x1f
#define MSTK_YEAR_MASK 0xffU
/* Binary coded decimal conversion macros. */
#define MSTK_REGVAL_TO_DECIMAL(x) (((x) & 0x0F) + 0x0A * ((x) >> 0x04))
#define MSTK_DECIMAL_TO_REGVAL(x) ((((x) / 0x0A) << 0x04) + ((x) % 0x0A))
/* Generic register set and get macros for internal use. */
#define MSTK_GET(regs,var,mask) (MSTK_REGVAL_TO_DECIMAL(((struct mostek48t02 *)regs)->var & MSTK_ ## mask ## _MASK))
#define MSTK_SET(regs,var,value,mask) do { ((struct mostek48t02 *)regs)->var &= ~(MSTK_ ## mask ## _MASK); ((struct mostek48t02 *)regs)->var |= MSTK_DECIMAL_TO_REGVAL(value) & (MSTK_ ## mask ## _MASK); } while (0)
/* Macros to make register access easier on our fingers. These give you
* the decimal value of the register requested if applicable. You pass
* the a pointer to a 'struct mostek48t02'.
*/
#define MSTK_REG_CREG(regs) (((struct mostek48t02 *)regs)->creg)
#define MSTK_REG_SEC(regs) MSTK_GET(regs,sec,SEC)
#define MSTK_REG_MIN(regs) MSTK_GET(regs,min,MIN)
#define MSTK_REG_HOUR(regs) MSTK_GET(regs,hour,HOUR)
#define MSTK_REG_DOW(regs) MSTK_GET(regs,dow,DOW)
#define MSTK_REG_DOM(regs) MSTK_GET(regs,dom,DOM)
#define MSTK_REG_MONTH(regs) MSTK_GET(regs,month,MONTH)
#define MSTK_REG_YEAR(regs) MSTK_GET(regs,year,YEAR)
#define MSTK_SET_REG_SEC(regs,value) MSTK_SET(regs,sec,value,SEC)
#define MSTK_SET_REG_MIN(regs,value) MSTK_SET(regs,min,value,MIN)
#define MSTK_SET_REG_HOUR(regs,value) MSTK_SET(regs,hour,value,HOUR)
#define MSTK_SET_REG_DOW(regs,value) MSTK_SET(regs,dow,value,DOW)
#define MSTK_SET_REG_DOM(regs,value) MSTK_SET(regs,dom,value,DOM)
#define MSTK_SET_REG_MONTH(regs,value) MSTK_SET(regs,month,value,MONTH)
#define MSTK_SET_REG_YEAR(regs,value) MSTK_SET(regs,year,value,YEAR)
/* The Mostek 48t08 clock chip. Found on Sun4m's I think. It has the
* same (basically) layout of the 48t02 chip except for the extra
* NVRAM on board (8 KB against the 48t02's 2 KB).
*/
struct mostek48t08 {
char offset[6*1024]; /* Magic things may be here, who knows? */
struct mostek48t02 regs; /* Here is what we are interested in. */
};
enum sparc_clock_type { MSTK48T02, MSTK48T08, MSTK_INVALID };
#endif /* !(_SPARC_MOSTEK_H) */
|