Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
L
linux
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
nexedi
linux
Commits
68da1c2a
Commit
68da1c2a
authored
May 23, 2004
by
Linus Torvalds
Browse files
Options
Browse Files
Download
Plain Diff
Merge
bk://bk.arm.linux.org.uk/linux-2.6-pcmcia
into ppc970.osdl.org:/home/torvalds/v2.6/linux
parents
9c2d00e7
a7336008
Changes
4
Show whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
55 additions
and
25 deletions
+55
-25
drivers/pcmcia/cs.c
drivers/pcmcia/cs.c
+13
-7
drivers/pcmcia/cs_internal.h
drivers/pcmcia/cs_internal.h
+3
-1
drivers/pcmcia/rsrc_mgr.c
drivers/pcmcia/rsrc_mgr.c
+38
-17
include/pcmcia/ss.h
include/pcmcia/ss.h
+1
-0
No files found.
drivers/pcmcia/cs.c
View file @
68da1c2a
...
@@ -789,9 +789,10 @@ static int alloc_io_space(struct pcmcia_socket *s, u_int attr, ioaddr_t *base,
...
@@ -789,9 +789,10 @@ static int alloc_io_space(struct pcmcia_socket *s, u_int attr, ioaddr_t *base,
return
1
;
return
1
;
for
(
i
=
0
;
i
<
MAX_IO_WIN
;
i
++
)
{
for
(
i
=
0
;
i
<
MAX_IO_WIN
;
i
++
)
{
if
(
s
->
io
[
i
].
NumPorts
==
0
)
{
if
(
s
->
io
[
i
].
NumPorts
==
0
)
{
if
(
find_io_region
(
base
,
num
,
align
,
name
,
s
)
==
0
)
{
s
->
io
[
i
].
res
=
find_io_region
(
*
base
,
num
,
align
,
name
,
s
);
if
(
s
->
io
[
i
].
res
)
{
s
->
io
[
i
].
Attributes
=
attr
;
s
->
io
[
i
].
Attributes
=
attr
;
s
->
io
[
i
].
BasePort
=
*
base
;
s
->
io
[
i
].
BasePort
=
*
base
=
s
->
io
[
i
].
res
->
start
;
s
->
io
[
i
].
NumPorts
=
s
->
io
[
i
].
InUse
=
num
;
s
->
io
[
i
].
NumPorts
=
s
->
io
[
i
].
InUse
=
num
;
break
;
break
;
}
else
}
else
...
@@ -801,7 +802,8 @@ static int alloc_io_space(struct pcmcia_socket *s, u_int attr, ioaddr_t *base,
...
@@ -801,7 +802,8 @@ static int alloc_io_space(struct pcmcia_socket *s, u_int attr, ioaddr_t *base,
/* Try to extend top of window */
/* Try to extend top of window */
try
=
s
->
io
[
i
].
BasePort
+
s
->
io
[
i
].
NumPorts
;
try
=
s
->
io
[
i
].
BasePort
+
s
->
io
[
i
].
NumPorts
;
if
((
*
base
==
0
)
||
(
*
base
==
try
))
if
((
*
base
==
0
)
||
(
*
base
==
try
))
if
(
find_io_region
(
&
try
,
num
,
0
,
name
,
s
)
==
0
)
{
if
(
adjust_io_region
(
s
->
io
[
i
].
res
,
s
->
io
[
i
].
res
->
start
,
s
->
io
[
i
].
res
->
end
+
num
,
s
)
==
0
)
{
*
base
=
try
;
*
base
=
try
;
s
->
io
[
i
].
NumPorts
+=
num
;
s
->
io
[
i
].
NumPorts
+=
num
;
s
->
io
[
i
].
InUse
+=
num
;
s
->
io
[
i
].
InUse
+=
num
;
...
@@ -810,7 +812,8 @@ static int alloc_io_space(struct pcmcia_socket *s, u_int attr, ioaddr_t *base,
...
@@ -810,7 +812,8 @@ static int alloc_io_space(struct pcmcia_socket *s, u_int attr, ioaddr_t *base,
/* Try to extend bottom of window */
/* Try to extend bottom of window */
try
=
s
->
io
[
i
].
BasePort
-
num
;
try
=
s
->
io
[
i
].
BasePort
-
num
;
if
((
*
base
==
0
)
||
(
*
base
==
try
))
if
((
*
base
==
0
)
||
(
*
base
==
try
))
if
(
find_io_region
(
&
try
,
num
,
0
,
name
,
s
)
==
0
)
{
if
(
adjust_io_region
(
s
->
io
[
i
].
res
,
s
->
io
[
i
].
res
->
start
-
num
,
s
->
io
[
i
].
res
->
end
,
s
)
==
0
)
{
s
->
io
[
i
].
BasePort
=
*
base
=
try
;
s
->
io
[
i
].
BasePort
=
*
base
=
try
;
s
->
io
[
i
].
NumPorts
+=
num
;
s
->
io
[
i
].
NumPorts
+=
num
;
s
->
io
[
i
].
InUse
+=
num
;
s
->
io
[
i
].
InUse
+=
num
;
...
@@ -824,15 +827,18 @@ static void release_io_space(struct pcmcia_socket *s, ioaddr_t base,
...
@@ -824,15 +827,18 @@ static void release_io_space(struct pcmcia_socket *s, ioaddr_t base,
ioaddr_t
num
)
ioaddr_t
num
)
{
{
int
i
;
int
i
;
if
(
!
(
s
->
features
&
SS_CAP_STATIC_MAP
))
release_region
(
base
,
num
);
for
(
i
=
0
;
i
<
MAX_IO_WIN
;
i
++
)
{
for
(
i
=
0
;
i
<
MAX_IO_WIN
;
i
++
)
{
if
((
s
->
io
[
i
].
BasePort
<=
base
)
&&
if
((
s
->
io
[
i
].
BasePort
<=
base
)
&&
(
s
->
io
[
i
].
BasePort
+
s
->
io
[
i
].
NumPorts
>=
base
+
num
))
{
(
s
->
io
[
i
].
BasePort
+
s
->
io
[
i
].
NumPorts
>=
base
+
num
))
{
s
->
io
[
i
].
InUse
-=
num
;
s
->
io
[
i
].
InUse
-=
num
;
/* Free the window if no one else is using it */
/* Free the window if no one else is using it */
if
(
s
->
io
[
i
].
InUse
==
0
)
if
(
s
->
io
[
i
].
InUse
==
0
)
{
s
->
io
[
i
].
NumPorts
=
0
;
s
->
io
[
i
].
NumPorts
=
0
;
release_resource
(
s
->
io
[
i
].
res
);
kfree
(
s
->
io
[
i
].
res
);
s
->
io
[
i
].
res
=
NULL
;
}
}
}
}
}
}
}
...
...
drivers/pcmcia/cs_internal.h
View file @
68da1c2a
...
@@ -181,8 +181,10 @@ int copy_memory(memory_handle_t handle, copy_op_t *req);
...
@@ -181,8 +181,10 @@ int copy_memory(memory_handle_t handle, copy_op_t *req);
/* In rsrc_mgr */
/* In rsrc_mgr */
void
validate_mem
(
struct
pcmcia_socket
*
s
);
void
validate_mem
(
struct
pcmcia_socket
*
s
);
int
find_io_region
(
ioaddr_t
*
base
,
ioaddr_
t
num
,
unsigned
long
align
,
struct
resource
*
find_io_region
(
unsigned
long
base
,
in
t
num
,
unsigned
long
align
,
char
*
name
,
struct
pcmcia_socket
*
s
);
char
*
name
,
struct
pcmcia_socket
*
s
);
int
adjust_io_region
(
struct
resource
*
res
,
unsigned
long
r_start
,
unsigned
long
r_end
,
struct
pcmcia_socket
*
s
);
int
find_mem_region
(
u_long
*
base
,
u_long
num
,
u_long
align
,
int
find_mem_region
(
u_long
*
base
,
u_long
num
,
u_long
align
,
int
low
,
char
*
name
,
struct
pcmcia_socket
*
s
);
int
low
,
char
*
name
,
struct
pcmcia_socket
*
s
);
int
try_irq
(
u_int
Attributes
,
int
irq
,
int
specific
);
int
try_irq
(
u_int
Attributes
,
int
irq
,
int
specific
);
...
...
drivers/pcmcia/rsrc_mgr.c
View file @
68da1c2a
...
@@ -550,7 +550,7 @@ pcmcia_align(void *align_data, struct resource *res,
...
@@ -550,7 +550,7 @@ pcmcia_align(void *align_data, struct resource *res,
for
(
m
=
data
->
map
->
next
;
m
!=
data
->
map
;
m
=
m
->
next
)
{
for
(
m
=
data
->
map
->
next
;
m
!=
data
->
map
;
m
=
m
->
next
)
{
unsigned
long
start
=
m
->
base
;
unsigned
long
start
=
m
->
base
;
unsigned
long
end
=
m
->
base
+
m
->
num
;
unsigned
long
end
=
m
->
base
+
m
->
num
-
1
;
/*
/*
* If the lower resources are not available, try aligning
* If the lower resources are not available, try aligning
...
@@ -569,7 +569,7 @@ pcmcia_align(void *align_data, struct resource *res,
...
@@ -569,7 +569,7 @@ pcmcia_align(void *align_data, struct resource *res,
if
(
res
->
start
>=
res
->
end
)
if
(
res
->
start
>=
res
->
end
)
break
;
break
;
if
((
res
->
start
+
size
)
<=
end
)
if
((
res
->
start
+
size
-
1
)
<=
end
)
break
;
break
;
}
}
...
@@ -580,6 +580,32 @@ pcmcia_align(void *align_data, struct resource *res,
...
@@ -580,6 +580,32 @@ pcmcia_align(void *align_data, struct resource *res,
res
->
start
=
res
->
end
;
res
->
start
=
res
->
end
;
}
}
/*
* Adjust an existing IO region allocation, but making sure that we don't
* encroach outside the resources which the user supplied.
*/
int
adjust_io_region
(
struct
resource
*
res
,
unsigned
long
r_start
,
unsigned
long
r_end
,
struct
pcmcia_socket
*
s
)
{
resource_map_t
*
m
;
int
ret
=
-
ENOMEM
;
down
(
&
rsrc_sem
);
for
(
m
=
io_db
.
next
;
m
!=
&
io_db
;
m
=
m
->
next
)
{
unsigned
long
start
=
m
->
base
;
unsigned
long
end
=
m
->
base
+
m
->
num
-
1
;
if
(
start
>
r_start
||
r_end
>
end
)
continue
;
ret
=
adjust_resource
(
res
,
r_start
,
r_end
-
r_start
+
1
);
break
;
}
up
(
&
rsrc_sem
);
return
ret
;
}
/*======================================================================
/*======================================================================
These find ranges of I/O ports or memory addresses that are not
These find ranges of I/O ports or memory addresses that are not
...
@@ -593,40 +619,37 @@ pcmcia_align(void *align_data, struct resource *res,
...
@@ -593,40 +619,37 @@ pcmcia_align(void *align_data, struct resource *res,
======================================================================*/
======================================================================*/
int
find_io_region
(
ioaddr_t
*
base
,
ioaddr_t
num
,
unsigned
long
align
,
struct
resource
*
find_io_region
(
unsigned
long
base
,
int
num
,
char
*
name
,
struct
pcmcia_socket
*
s
)
unsigned
long
align
,
char
*
name
,
struct
pcmcia_socket
*
s
)
{
{
struct
resource
*
res
=
make_resource
(
0
,
num
,
IORESOURCE_IO
,
name
);
struct
resource
*
res
=
make_resource
(
0
,
num
,
IORESOURCE_IO
,
name
);
struct
pcmcia_align_data
data
;
struct
pcmcia_align_data
data
;
unsigned
long
min
=
*
base
;
unsigned
long
min
=
base
;
int
ret
;
int
ret
;
if
(
align
==
0
)
if
(
align
==
0
)
align
=
0x10000
;
align
=
0x10000
;
data
.
mask
=
align
-
1
;
data
.
mask
=
align
-
1
;
data
.
offset
=
*
base
&
data
.
mask
;
data
.
offset
=
base
&
data
.
mask
;
data
.
map
=
&
io_db
;
data
.
map
=
&
io_db
;
down
(
&
rsrc_sem
);
#ifdef CONFIG_PCI
#ifdef CONFIG_PCI
if
(
s
->
cb_dev
)
{
if
(
s
->
cb_dev
)
{
ret
=
pci_bus_alloc_resource
(
s
->
cb_dev
->
bus
,
res
,
num
,
1
,
ret
=
pci_bus_alloc_resource
(
s
->
cb_dev
->
bus
,
res
,
num
,
1
,
min
,
0
,
pcmcia_align
,
&
data
);
min
,
0
,
pcmcia_align
,
&
data
);
}
else
}
else
#endif
#endif
{
down
(
&
rsrc_sem
);
ret
=
allocate_resource
(
&
ioport_resource
,
res
,
num
,
min
,
~
0UL
,
0
,
ret
=
allocate_resource
(
&
ioport_resource
,
res
,
num
,
min
,
~
0UL
,
0
,
pcmcia_align
,
&
data
);
pcmcia_align
,
&
data
);
up
(
&
rsrc_sem
);
up
(
&
rsrc_sem
);
}
if
(
ret
!=
0
)
{
if
(
ret
!=
0
)
{
kfree
(
res
);
kfree
(
res
);
}
else
{
res
=
NULL
;
*
base
=
res
->
start
;
}
}
return
re
t
;
return
re
s
;
}
}
int
find_mem_region
(
u_long
*
base
,
u_long
num
,
u_long
align
,
int
find_mem_region
(
u_long
*
base
,
u_long
num
,
u_long
align
,
...
@@ -652,6 +675,7 @@ int find_mem_region(u_long *base, u_long num, u_long align,
...
@@ -652,6 +675,7 @@ int find_mem_region(u_long *base, u_long num, u_long align,
min
=
0x100000UL
+
*
base
;
min
=
0x100000UL
+
*
base
;
}
}
down
(
&
rsrc_sem
);
#ifdef CONFIG_PCI
#ifdef CONFIG_PCI
if
(
s
->
cb_dev
)
{
if
(
s
->
cb_dev
)
{
ret
=
pci_bus_alloc_resource
(
s
->
cb_dev
->
bus
,
res
,
num
,
ret
=
pci_bus_alloc_resource
(
s
->
cb_dev
->
bus
,
res
,
num
,
...
@@ -659,12 +683,9 @@ int find_mem_region(u_long *base, u_long num, u_long align,
...
@@ -659,12 +683,9 @@ int find_mem_region(u_long *base, u_long num, u_long align,
pcmcia_align
,
&
data
);
pcmcia_align
,
&
data
);
}
else
}
else
#endif
#endif
{
down
(
&
rsrc_sem
);
ret
=
allocate_resource
(
&
iomem_resource
,
res
,
num
,
min
,
ret
=
allocate_resource
(
&
iomem_resource
,
res
,
num
,
min
,
max
,
0
,
pcmcia_align
,
&
data
);
max
,
0
,
pcmcia_align
,
&
data
);
up
(
&
rsrc_sem
);
up
(
&
rsrc_sem
);
}
if
(
ret
==
0
||
low
)
if
(
ret
==
0
||
low
)
break
;
break
;
low
=
1
;
low
=
1
;
...
...
include/pcmcia/ss.h
View file @
68da1c2a
...
@@ -145,6 +145,7 @@ typedef struct io_window_t {
...
@@ -145,6 +145,7 @@ typedef struct io_window_t {
u_int
Attributes
;
u_int
Attributes
;
ioaddr_t
BasePort
,
NumPorts
;
ioaddr_t
BasePort
,
NumPorts
;
ioaddr_t
InUse
,
Config
;
ioaddr_t
InUse
,
Config
;
struct
resource
*
res
;
}
io_window_t
;
}
io_window_t
;
#define WINDOW_MAGIC 0xB35C
#define WINDOW_MAGIC 0xB35C
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment