svn commit: r237399 - in user/ae/bootcode: bin/rm
etc/periodic/daily lib/libc/string share/man/man4
sys/amd64/amd64 sys/boot/common sys/cam sys/cam/scsi
sys/dev/puc sys/dev/viawd sys/dev/xen/balloo...
Andrey V. Elsukov
ae at FreeBSD.org
Thu Jun 21 14:37:06 UTC 2012
Author: ae
Date: Thu Jun 21 14:37:05 2012
New Revision: 237399
URL: http://svn.freebsd.org/changeset/base/237399
Log:
Sync with head/.
Modified:
user/ae/bootcode/bin/rm/rm.c
user/ae/bootcode/etc/periodic/daily/400.status-disks
user/ae/bootcode/lib/libc/string/strcasecmp.3
user/ae/bootcode/lib/libc/string/strcoll.3
user/ae/bootcode/lib/libc/string/strstr.3
user/ae/bootcode/lib/libc/string/strxfrm.3
user/ae/bootcode/share/man/man4/cpufreq.4
user/ae/bootcode/sys/amd64/amd64/pmap.c
user/ae/bootcode/sys/boot/common/load_elf.c
user/ae/bootcode/sys/boot/common/load_elf_obj.c
user/ae/bootcode/sys/cam/cam_periph.c
user/ae/bootcode/sys/cam/cam_xpt.c
user/ae/bootcode/sys/cam/cam_xpt_periph.h
user/ae/bootcode/sys/cam/scsi/scsi_cd.c
user/ae/bootcode/sys/cam/scsi/scsi_da.c
user/ae/bootcode/sys/cam/scsi/scsi_enc.c
user/ae/bootcode/sys/cam/scsi/scsi_pass.c
user/ae/bootcode/sys/dev/puc/puc_cfg.h
user/ae/bootcode/sys/dev/puc/pucdata.c
user/ae/bootcode/sys/dev/viawd/viawd.c
user/ae/bootcode/sys/dev/xen/balloon/balloon.c
user/ae/bootcode/sys/fs/nfsclient/nfs_clbio.c
user/ae/bootcode/sys/fs/nfsclient/nfs_clvfsops.c
user/ae/bootcode/sys/kern/vfs_vnops.c
user/ae/bootcode/sys/netinet/sctp_usrreq.c
user/ae/bootcode/sys/ufs/ffs/ffs_vnops.c
user/ae/bootcode/sys/vm/vm_map.c
user/ae/bootcode/sys/vm/vm_page.c
user/ae/bootcode/sys/vm/vm_page.h
user/ae/bootcode/tools/regression/usr.bin/make/common.sh
user/ae/bootcode/usr.bin/makewhatis/makewhatis.c
user/ae/bootcode/usr.sbin/mfiutil/mfi_drive.c
Directory Properties:
user/ae/bootcode/ (props changed)
user/ae/bootcode/lib/libc/ (props changed)
user/ae/bootcode/share/man/man4/ (props changed)
user/ae/bootcode/sys/ (props changed)
user/ae/bootcode/sys/boot/ (props changed)
Modified: user/ae/bootcode/bin/rm/rm.c
==============================================================================
--- user/ae/bootcode/bin/rm/rm.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/bin/rm/rm.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -301,10 +301,16 @@ rm_tree(char **argv)
if (fflag)
continue;
/* FALLTHROUGH */
- default:
+
+ case FTS_F:
+ case FTS_NSOK:
if (Pflag)
- if (!rm_overwrite(p->fts_accpath, NULL))
+ if (!rm_overwrite(p->fts_accpath, p->fts_info ==
+ FTS_NSOK ? NULL : p->fts_statp))
continue;
+ /* FALLTHROUGH */
+
+ default:
rval = unlink(p->fts_accpath);
if (rval == 0 || (fflag && errno == ENOENT)) {
if (rval == 0 && vflag)
Modified: user/ae/bootcode/etc/periodic/daily/400.status-disks
==============================================================================
--- user/ae/bootcode/etc/periodic/daily/400.status-disks Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/etc/periodic/daily/400.status-disks Thu Jun 21 14:37:05 2012 (r237399)
@@ -19,12 +19,15 @@ case "$daily_status_disks_enable" in
df $daily_status_disks_df_flags && rc=1 || rc=3
# display which filesystems need backing up
- if ! [ -f /etc/fstab ]; then
- export PATH_FSTAB=/dev/null
- fi
+ if [ -s /etc/dumpdates ]; then
+ if ! [ -f /etc/fstab ]; then
+ export PATH_FSTAB=/dev/null
+ fi
- echo ""
- dump W || rc=3;;
+ echo ""
+ dump W || rc=3
+ fi
+ ;;
*) rc=0;;
esac
Modified: user/ae/bootcode/lib/libc/string/strcasecmp.3
==============================================================================
--- user/ae/bootcode/lib/libc/string/strcasecmp.3 Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/lib/libc/string/strcasecmp.3 Thu Jun 21 14:37:05 2012 (r237399)
@@ -45,6 +45,12 @@
.Fn strcasecmp "const char *s1" "const char *s2"
.Ft int
.Fn strncasecmp "const char *s1" "const char *s2" "size_t len"
+.In string.h
+.In xlocale.h
+.Ft int
+.Fn strcasecmp_l "const char *s1" "const char *s2" "locale_t loc"
+.Ft int
+.Fn strncasecmp_l "const char *s1" "const char *s2" "site_t len" "locale_t loc"
.Sh DESCRIPTION
The
.Fn strcasecmp
@@ -58,16 +64,22 @@ and
.Pp
The
.Fn strncasecmp
-compares at most
+function compares at most
.Fa len
characters.
-.Sh RETURN VALUES
The
+.Fn strcasecmp_l
+and
+.Fn strncasecmp_l
+functions do the same as their non-locale versions above, but take an
+explicit locale rather than using the current locale.
+.Sh RETURN VALUES
+The functions
.Fn strcasecmp
and
.Fn strncasecmp
return an integer greater than, equal to, or less than 0,
-according as
+depending on whether
.Fa s1
is lexicographically greater than, equal to, or less than
.Fa s2
@@ -77,6 +89,11 @@ The comparison is done using unsigned ch
.Sq Li \e200
is greater than
.Ql \e0 .
+The functions
+.Fn strcasecmp_l
+and
+.Fn strncasecmp_l
+do the same but take explicit locales.
.Sh SEE ALSO
.Xr bcmp 3 ,
.Xr memcmp 3 ,
Modified: user/ae/bootcode/lib/libc/string/strcoll.3
==============================================================================
--- user/ae/bootcode/lib/libc/string/strcoll.3 Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/lib/libc/string/strcoll.3 Thu Jun 21 14:37:05 2012 (r237399)
@@ -44,6 +44,8 @@
.In string.h
.Ft int
.Fn strcoll "const char *s1" "const char *s2"
+.Ft int
+.Fn strcoll_l "const char *s1" "const char *s2" "locale_t loc"
.Sh DESCRIPTION
The
.Fn strcoll
@@ -54,7 +56,7 @@ and
.Fa s2
according to the current locale collation
and returns an integer greater than, equal to, or less than 0,
-according as
+depending on whether
.Fa s1
is greater than, equal to, or less than
.Fa s2 .
@@ -62,6 +64,9 @@ If information about the current locale
the value of
.Fn strcmp s1 s2
is returned.
+The
+.Fn strcoll_l
+function uses an explicit locale argument rather than the system locale.
.Sh SEE ALSO
.Xr setlocale 3 ,
.Xr strcmp 3 ,
@@ -70,6 +75,9 @@ is returned.
.Sh STANDARDS
The
.Fn strcoll
-function
-conforms to
+function conforms to
.St -isoC .
+The
+.Fn strcoll_l
+function conforms to
+.St -p1003.1-2008 .
Modified: user/ae/bootcode/lib/libc/string/strstr.3
==============================================================================
--- user/ae/bootcode/lib/libc/string/strstr.3 Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/lib/libc/string/strstr.3 Thu Jun 21 14:37:05 2012 (r237399)
@@ -49,6 +49,10 @@
.Fn strcasestr "const char *big" "const char *little"
.Ft char *
.Fn strnstr "const char *big" "const char *little" "size_t len"
+.In string.h
+.In xlocale.h
+.Ft char *
+.Fn strcasestr_l "const char *big" "const char *little" "locale_t loc"
.Sh DESCRIPTION
The
.Fn strstr
@@ -65,6 +69,12 @@ function is similar to
but ignores the case of both strings.
.Pp
The
+.Fn strcasestr_l
+function does the same as
+.Fn strcasestr
+but takes an explicit locale rather than using the current locale.
+.Pp
+The
.Fn strnstr
function
locates the first occurrence of the null-terminated string
Modified: user/ae/bootcode/lib/libc/string/strxfrm.3
==============================================================================
--- user/ae/bootcode/lib/libc/string/strxfrm.3 Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/lib/libc/string/strxfrm.3 Thu Jun 21 14:37:05 2012 (r237399)
@@ -44,6 +44,8 @@
.In string.h
.Ft size_t
.Fn strxfrm "char * restrict dst" "const char * restrict src" "size_t n"
+.Ft size_t
+.Fn strxfrm_l "char * restrict dst" "const char *restrict src" "size_t n" "locale_t loc"
.Sh DESCRIPTION
The
.Fn strxfrm
@@ -73,10 +75,16 @@ after
is equal to comparing
two original strings with
.Fn strcoll .
+.Pp
+.Fn strxfrm_l
+does the same, however takes an explicit locale rather than the global
+locale.
.Sh RETURN VALUES
Upon successful completion,
.Fn strxfrm
-returns the length of the transformed string not including
+and
+.Fn strxfrm_l
+return the length of the transformed string not including
the terminating null character.
If this value is
.Fa n
@@ -94,3 +102,7 @@ The
function
conforms to
.St -isoC .
+The
+.Fn strxfrm_l
+function conforms to
+.St -p1003.1-2008 .
Modified: user/ae/bootcode/share/man/man4/cpufreq.4
==============================================================================
--- user/ae/bootcode/share/man/man4/cpufreq.4 Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/share/man/man4/cpufreq.4 Thu Jun 21 14:37:05 2012 (r237399)
@@ -286,6 +286,7 @@ then it should set all elements to
.Dv CPUFREQ_VAL_UNKNOWN .
.Sh SEE ALSO
.Xr acpi 4 ,
+.Xr est 4 ,
.Xr timecounters 4 ,
.Xr powerd 8 ,
.Xr sysctl 8
Modified: user/ae/bootcode/sys/amd64/amd64/pmap.c
==============================================================================
--- user/ae/bootcode/sys/amd64/amd64/pmap.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/amd64/amd64/pmap.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -241,7 +241,8 @@ static void free_pv_chunk(struct pv_chun
static void free_pv_entry(pmap_t pmap, pv_entry_t pv);
static pv_entry_t get_pv_entry(pmap_t pmap, boolean_t try);
static void pmap_pv_demote_pde(pmap_t pmap, vm_offset_t va, vm_paddr_t pa);
-static boolean_t pmap_pv_insert_pde(pmap_t pmap, vm_offset_t va, vm_paddr_t pa);
+static boolean_t pmap_pv_insert_pde(pmap_t pmap, vm_offset_t va, vm_paddr_t pa,
+ struct rwlock **lockp);
static void pmap_pv_promote_pde(pmap_t pmap, vm_offset_t va, vm_paddr_t pa);
static void pmap_pvh_free(struct md_page *pvh, pmap_t pmap, vm_offset_t va);
static pv_entry_t pmap_pvh_remove(struct md_page *pvh, pmap_t pmap,
@@ -253,9 +254,9 @@ static boolean_t pmap_demote_pde(pmap_t
static boolean_t pmap_demote_pdpe(pmap_t pmap, pdp_entry_t *pdpe,
vm_offset_t va);
static boolean_t pmap_enter_pde(pmap_t pmap, vm_offset_t va, vm_page_t m,
- vm_prot_t prot);
+ vm_prot_t prot, struct rwlock **lockp);
static vm_page_t pmap_enter_quick_locked(pmap_t pmap, vm_offset_t va,
- vm_page_t m, vm_prot_t prot, vm_page_t mpte);
+ vm_page_t m, vm_prot_t prot, vm_page_t mpte, struct rwlock **lockp);
static void pmap_fill_ptp(pt_entry_t *firstpte, pt_entry_t newpte);
static void pmap_insert_pt_page(pmap_t pmap, vm_page_t mpte);
static boolean_t pmap_is_modified_pvh(struct md_page *pvh);
@@ -278,7 +279,7 @@ static void pmap_remove_entry(struct pma
vm_offset_t va);
static void pmap_insert_entry(pmap_t pmap, vm_offset_t va, vm_page_t m);
static boolean_t pmap_try_insert_pv_entry(pmap_t pmap, vm_offset_t va,
- vm_page_t m);
+ vm_page_t m, struct rwlock **lockp);
static void pmap_update_pde(pmap_t pmap, vm_offset_t va, pd_entry_t *pde,
pd_entry_t newpde);
static void pmap_update_pde_invalidate(vm_offset_t va, pd_entry_t newpde);
@@ -2463,14 +2464,23 @@ pmap_insert_entry(pmap_t pmap, vm_offset
* Conditionally create a pv entry.
*/
static boolean_t
-pmap_try_insert_pv_entry(pmap_t pmap, vm_offset_t va, vm_page_t m)
+pmap_try_insert_pv_entry(pmap_t pmap, vm_offset_t va, vm_page_t m,
+ struct rwlock **lockp)
{
+ struct rwlock *new_lock;
pv_entry_t pv;
- rw_assert(&pvh_global_lock, RA_WLOCKED);
+ rw_assert(&pvh_global_lock, RA_LOCKED);
PMAP_LOCK_ASSERT(pmap, MA_OWNED);
if ((pv = get_pv_entry(pmap, TRUE)) != NULL) {
pv->pv_va = va;
+ new_lock = VM_PAGE_TO_PV_LIST_LOCK(m);
+ if (new_lock != *lockp) {
+ if (*lockp != NULL)
+ rw_wunlock(*lockp);
+ *lockp = new_lock;
+ rw_wlock(*lockp);
+ }
TAILQ_INSERT_TAIL(&m->md.pv_list, pv, pv_list);
return (TRUE);
} else
@@ -2481,14 +2491,23 @@ pmap_try_insert_pv_entry(pmap_t pmap, vm
* Create the pv entry for a 2MB page mapping.
*/
static boolean_t
-pmap_pv_insert_pde(pmap_t pmap, vm_offset_t va, vm_paddr_t pa)
+pmap_pv_insert_pde(pmap_t pmap, vm_offset_t va, vm_paddr_t pa,
+ struct rwlock **lockp)
{
struct md_page *pvh;
+ struct rwlock *new_lock;
pv_entry_t pv;
- rw_assert(&pvh_global_lock, RA_WLOCKED);
+ rw_assert(&pvh_global_lock, RA_LOCKED);
if ((pv = get_pv_entry(pmap, TRUE)) != NULL) {
pv->pv_va = va;
+ new_lock = PHYS_TO_PV_LIST_LOCK(pa);
+ if (new_lock != *lockp) {
+ if (*lockp != NULL)
+ rw_wunlock(*lockp);
+ *lockp = new_lock;
+ rw_wlock(*lockp);
+ }
pvh = pa_to_pvh(pa);
TAILQ_INSERT_TAIL(&pvh->pv_list, pv, pv_list);
return (TRUE);
@@ -3434,12 +3453,13 @@ validate:
* (3) a pv entry cannot be allocated without reclaiming another pv entry.
*/
static boolean_t
-pmap_enter_pde(pmap_t pmap, vm_offset_t va, vm_page_t m, vm_prot_t prot)
+pmap_enter_pde(pmap_t pmap, vm_offset_t va, vm_page_t m, vm_prot_t prot,
+ struct rwlock **lockp)
{
pd_entry_t *pde, newpde;
vm_page_t free, mpde;
- rw_assert(&pvh_global_lock, RA_WLOCKED);
+ rw_assert(&pvh_global_lock, RA_LOCKED);
PMAP_LOCK_ASSERT(pmap, MA_OWNED);
if ((mpde = pmap_allocpde(pmap, va, M_NOWAIT)) == NULL) {
CTR2(KTR_PMAP, "pmap_enter_pde: failure for va %#lx"
@@ -3464,7 +3484,8 @@ pmap_enter_pde(pmap_t pmap, vm_offset_t
/*
* Abort this mapping if its PV entry could not be created.
*/
- if (!pmap_pv_insert_pde(pmap, va, VM_PAGE_TO_PHYS(m))) {
+ if (!pmap_pv_insert_pde(pmap, va, VM_PAGE_TO_PHYS(m),
+ lockp)) {
free = NULL;
if (pmap_unwire_pte_hold(pmap, va, mpde, &free)) {
pmap_invalidate_page(pmap, va);
@@ -3490,7 +3511,7 @@ pmap_enter_pde(pmap_t pmap, vm_offset_t
*/
pde_store(pde, newpde);
- pmap_pde_mappings++;
+ atomic_add_long(&pmap_pde_mappings, 1);
CTR2(KTR_PMAP, "pmap_enter_pde: success for va %#lx"
" in pmap %p", va, pmap);
return (TRUE);
@@ -3512,6 +3533,7 @@ void
pmap_enter_object(pmap_t pmap, vm_offset_t start, vm_offset_t end,
vm_page_t m_start, vm_prot_t prot)
{
+ struct rwlock *lock;
vm_offset_t va;
vm_page_t m, mpte;
vm_pindex_t diff, psize;
@@ -3520,21 +3542,24 @@ pmap_enter_object(pmap_t pmap, vm_offset
psize = atop(end - start);
mpte = NULL;
m = m_start;
- rw_wlock(&pvh_global_lock);
+ lock = NULL;
+ rw_rlock(&pvh_global_lock);
PMAP_LOCK(pmap);
while (m != NULL && (diff = m->pindex - m_start->pindex) < psize) {
va = start + ptoa(diff);
if ((va & PDRMASK) == 0 && va + NBPDR <= end &&
(VM_PAGE_TO_PHYS(m) & PDRMASK) == 0 &&
pg_ps_enabled && vm_reserv_level_iffullpop(m) == 0 &&
- pmap_enter_pde(pmap, va, m, prot))
+ pmap_enter_pde(pmap, va, m, prot, &lock))
m = &m[NBPDR / PAGE_SIZE - 1];
else
mpte = pmap_enter_quick_locked(pmap, va, m, prot,
- mpte);
+ mpte, &lock);
m = TAILQ_NEXT(m, listq);
}
- rw_wunlock(&pvh_global_lock);
+ if (lock != NULL)
+ rw_wunlock(lock);
+ rw_runlock(&pvh_global_lock);
PMAP_UNLOCK(pmap);
}
@@ -3550,17 +3575,21 @@ pmap_enter_object(pmap_t pmap, vm_offset
void
pmap_enter_quick(pmap_t pmap, vm_offset_t va, vm_page_t m, vm_prot_t prot)
{
+ struct rwlock *lock;
- rw_wlock(&pvh_global_lock);
+ lock = NULL;
+ rw_rlock(&pvh_global_lock);
PMAP_LOCK(pmap);
- (void)pmap_enter_quick_locked(pmap, va, m, prot, NULL);
- rw_wunlock(&pvh_global_lock);
+ (void)pmap_enter_quick_locked(pmap, va, m, prot, NULL, &lock);
+ if (lock != NULL)
+ rw_wunlock(lock);
+ rw_runlock(&pvh_global_lock);
PMAP_UNLOCK(pmap);
}
static vm_page_t
pmap_enter_quick_locked(pmap_t pmap, vm_offset_t va, vm_page_t m,
- vm_prot_t prot, vm_page_t mpte)
+ vm_prot_t prot, vm_page_t mpte, struct rwlock **lockp)
{
vm_page_t free;
pt_entry_t *pte;
@@ -3569,7 +3598,7 @@ pmap_enter_quick_locked(pmap_t pmap, vm_
KASSERT(va < kmi.clean_sva || va >= kmi.clean_eva ||
(m->oflags & VPO_UNMANAGED) != 0,
("pmap_enter_quick_locked: managed mapping within the clean submap"));
- rw_assert(&pvh_global_lock, RA_WLOCKED);
+ rw_assert(&pvh_global_lock, RA_LOCKED);
PMAP_LOCK_ASSERT(pmap, MA_OWNED);
/*
@@ -3626,7 +3655,7 @@ pmap_enter_quick_locked(pmap_t pmap, vm_
* Enter on the PV list if part of our managed memory.
*/
if ((m->oflags & VPO_UNMANAGED) == 0 &&
- !pmap_try_insert_pv_entry(pmap, va, m)) {
+ !pmap_try_insert_pv_entry(pmap, va, m, lockp)) {
if (mpte != NULL) {
free = NULL;
if (pmap_unwire_pte_hold(pmap, va, mpte, &free)) {
@@ -3825,6 +3854,7 @@ void
pmap_copy(pmap_t dst_pmap, pmap_t src_pmap, vm_offset_t dst_addr, vm_size_t len,
vm_offset_t src_addr)
{
+ struct rwlock *lock;
vm_page_t free;
vm_offset_t addr;
vm_offset_t end_addr = src_addr + len;
@@ -3833,7 +3863,8 @@ pmap_copy(pmap_t dst_pmap, pmap_t src_pm
if (dst_addr != src_addr)
return;
- rw_wlock(&pvh_global_lock);
+ lock = NULL;
+ rw_rlock(&pvh_global_lock);
if (dst_pmap < src_pmap) {
PMAP_LOCK(dst_pmap);
PMAP_LOCK(src_pmap);
@@ -3885,7 +3916,7 @@ pmap_copy(pmap_t dst_pmap, pmap_t src_pm
pde = &pde[pmap_pde_index(addr)];
if (*pde == 0 && ((srcptepaddr & PG_MANAGED) == 0 ||
pmap_pv_insert_pde(dst_pmap, addr, srcptepaddr &
- PG_PS_FRAME))) {
+ PG_PS_FRAME, &lock))) {
*pde = srcptepaddr & ~PG_W;
pmap_resident_count_inc(dst_pmap, NBPDR / PAGE_SIZE);
} else
@@ -3922,7 +3953,8 @@ pmap_copy(pmap_t dst_pmap, pmap_t src_pm
dst_pte = &dst_pte[pmap_pte_index(addr)];
if (*dst_pte == 0 &&
pmap_try_insert_pv_entry(dst_pmap, addr,
- PHYS_TO_VM_PAGE(ptetemp & PG_FRAME))) {
+ PHYS_TO_VM_PAGE(ptetemp & PG_FRAME),
+ &lock)) {
/*
* Clear the wired, modified, and
* accessed (referenced) bits
@@ -3949,7 +3981,9 @@ pmap_copy(pmap_t dst_pmap, pmap_t src_pm
}
}
out:
- rw_wunlock(&pvh_global_lock);
+ if (lock != NULL)
+ rw_wunlock(lock);
+ rw_runlock(&pvh_global_lock);
PMAP_UNLOCK(src_pmap);
PMAP_UNLOCK(dst_pmap);
}
@@ -4158,9 +4192,9 @@ pmap_remove_pages(pmap_t pmap)
printf("warning: pmap_remove_pages called with non-current pmap\n");
return;
}
+ lock = NULL;
rw_rlock(&pvh_global_lock);
PMAP_LOCK(pmap);
- lock = NULL;
TAILQ_FOREACH_SAFE(pc, &pmap->pm_pvchunk, pc_list, npc) {
allfree = 1;
freed = 0;
@@ -4268,10 +4302,6 @@ pmap_remove_pages(pmap_t pmap)
PV_STAT(atomic_add_int(&pv_entry_spare, freed));
PV_STAT(atomic_subtract_long(&pv_entry_count, freed));
if (allfree) {
- if (lock != NULL) {
- rw_wunlock(lock);
- lock = NULL;
- }
TAILQ_REMOVE(&pmap->pm_pvchunk, pc, pc_list);
free_pv_chunk(pc);
}
Modified: user/ae/bootcode/sys/boot/common/load_elf.c
==============================================================================
--- user/ae/bootcode/sys/boot/common/load_elf.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/boot/common/load_elf.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -612,7 +612,7 @@ __elfN(parse_modmetadata)(struct preload
Elf_Addr v, p, p_stop;
if (__elfN(lookup_symbol)(fp, ef, "__start_set_modmetadata_set", &sym) != 0)
- return ENOENT;
+ return 0;
p = sym.st_value + ef->off;
if (__elfN(lookup_symbol)(fp, ef, "__stop_set_modmetadata_set", &sym) != 0)
return ENOENT;
Modified: user/ae/bootcode/sys/boot/common/load_elf_obj.c
==============================================================================
--- user/ae/bootcode/sys/boot/common/load_elf_obj.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/boot/common/load_elf_obj.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -369,7 +369,7 @@ __elfN(obj_parse_modmetadata)(struct pre
if (__elfN(obj_lookup_set)(fp, ef, "modmetadata_set", &p, &p_stop,
&modcnt) != 0)
- return ENOENT;
+ return 0;
modcnt = 0;
while (p < p_stop) {
Modified: user/ae/bootcode/sys/cam/cam_periph.c
==============================================================================
--- user/ae/bootcode/sys/cam/cam_periph.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/cam/cam_periph.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -258,7 +258,7 @@ failure:
break;
case 3:
CAM_DEBUG(periph->path, CAM_DEBUG_INFO, ("Periph destroyed\n"));
- xpt_remove_periph(periph);
+ xpt_remove_periph(periph, /*topology_lock_held*/ 0);
/* FALLTHROUGH */
case 2:
xpt_lock_buses();
@@ -610,13 +610,38 @@ camperiphfree(struct cam_periph *periph)
return;
}
- TAILQ_REMOVE(&(*p_drv)->units, periph, unit_links);
- (*p_drv)->generation++;
+ /*
+ * The peripheral destructor semantics dictate calling with only the
+ * SIM mutex held. Since it might sleep, it should not be called
+ * with the topology lock held.
+ */
xpt_unlock_buses();
+ /*
+ * We need to call the peripheral destructor prior to removing the
+ * peripheral from the list. Otherwise, we risk running into a
+ * scenario where the peripheral unit number may get reused
+ * (because it has been removed from the list), but some resources
+ * used by the peripheral are still hanging around. In particular,
+ * the devfs nodes used by some peripherals like the pass(4) driver
+ * aren't fully cleaned up until the destructor is run. If the
+ * unit number is reused before the devfs instance is fully gone,
+ * devfs will panic.
+ */
if (periph->periph_dtor != NULL)
periph->periph_dtor(periph);
- xpt_remove_periph(periph);
+
+ /*
+ * The peripheral list is protected by the topology lock.
+ */
+ xpt_lock_buses();
+
+ TAILQ_REMOVE(&(*p_drv)->units, periph, unit_links);
+ (*p_drv)->generation++;
+
+ xpt_remove_periph(periph, /*topology_lock_held*/ 1);
+
+ xpt_unlock_buses();
CAM_DEBUG(periph->path, CAM_DEBUG_INFO, ("Periph destroyed\n"));
if (periph->flags & CAM_PERIPH_NEW_DEV_FOUND) {
Modified: user/ae/bootcode/sys/cam/cam_xpt.c
==============================================================================
--- user/ae/bootcode/sys/cam/cam_xpt.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/cam/cam_xpt.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -1026,7 +1026,7 @@ xpt_add_periph(struct cam_periph *periph
}
void
-xpt_remove_periph(struct cam_periph *periph)
+xpt_remove_periph(struct cam_periph *periph, int topology_lock_held)
{
struct cam_ed *device;
@@ -1047,9 +1047,13 @@ xpt_remove_periph(struct cam_periph *per
SLIST_REMOVE(periph_head, periph, cam_periph, periph_links);
}
- mtx_lock(&xsoftc.xpt_topo_lock);
+ if (topology_lock_held == 0)
+ mtx_lock(&xsoftc.xpt_topo_lock);
+
xsoftc.xpt_generation++;
- mtx_unlock(&xsoftc.xpt_topo_lock);
+
+ if (topology_lock_held == 0)
+ mtx_unlock(&xsoftc.xpt_topo_lock);
}
Modified: user/ae/bootcode/sys/cam/cam_xpt_periph.h
==============================================================================
--- user/ae/bootcode/sys/cam/cam_xpt_periph.h Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/cam/cam_xpt_periph.h Thu Jun 21 14:37:05 2012 (r237399)
@@ -42,7 +42,8 @@ void xpt_polled_action(union ccb *ccb);
void xpt_release_ccb(union ccb *released_ccb);
void xpt_schedule(struct cam_periph *perph, u_int32_t new_priority);
int32_t xpt_add_periph(struct cam_periph *periph);
-void xpt_remove_periph(struct cam_periph *periph);
+void xpt_remove_periph(struct cam_periph *periph,
+ int topology_lock_held);
void xpt_announce_periph(struct cam_periph *periph,
char *announce_string);
#endif
Modified: user/ae/bootcode/sys/cam/scsi/scsi_cd.c
==============================================================================
--- user/ae/bootcode/sys/cam/scsi/scsi_cd.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/cam/scsi/scsi_cd.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -1049,7 +1049,11 @@ cdclose(struct disk *dp)
softc = (struct cd_softc *)periph->softc;
cam_periph_lock(periph);
- cam_periph_hold(periph, PRIBIO);
+ if (cam_periph_hold(periph, PRIBIO) != 0) {
+ cam_periph_unlock(periph);
+ cam_periph_release(periph);
+ return (0);
+ }
CAM_DEBUG(periph->path, CAM_DEBUG_TRACE | CAM_DEBUG_PERIPH,
("cdclose\n"));
Modified: user/ae/bootcode/sys/cam/scsi/scsi_da.c
==============================================================================
--- user/ae/bootcode/sys/cam/scsi/scsi_da.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/cam/scsi/scsi_da.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -982,14 +982,13 @@ daclose(struct disk *dp)
{
struct cam_periph *periph;
struct da_softc *softc;
- int error;
periph = (struct cam_periph *)dp->d_drv1;
if (periph == NULL)
return (0);
cam_periph_lock(periph);
- if ((error = cam_periph_hold(periph, PRIBIO)) != 0) {
+ if (cam_periph_hold(periph, PRIBIO) != 0) {
cam_periph_unlock(periph);
cam_periph_release(periph);
return (0);
Modified: user/ae/bootcode/sys/cam/scsi/scsi_enc.c
==============================================================================
--- user/ae/bootcode/sys/cam/scsi/scsi_enc.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/cam/scsi/scsi_enc.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -114,6 +114,16 @@ enc_init(void)
}
static void
+enc_devgonecb(void *arg)
+{
+ struct cam_periph *periph;
+
+ periph = (struct cam_periph *)arg;
+
+ cam_periph_release(periph);
+}
+
+static void
enc_oninvalidate(struct cam_periph *periph)
{
struct enc_softc *enc;
@@ -141,6 +151,8 @@ enc_oninvalidate(struct cam_periph *peri
}
callout_drain(&enc->status_updater);
+ destroy_dev_sched_cb(enc->enc_dev, enc_devgonecb, periph);
+
xpt_print(periph->path, "lost device\n");
}
@@ -152,9 +164,7 @@ enc_dtor(struct cam_periph *periph)
enc = periph->softc;
xpt_print(periph->path, "removing device entry\n");
- cam_periph_unlock(periph);
- destroy_dev(enc->enc_dev);
- cam_periph_lock(periph);
+
/* If the sub-driver has a cleanup routine, call it */
if (enc->enc_vec.softc_cleanup != NULL)
@@ -951,9 +961,19 @@ enc_ctor(struct cam_periph *periph, void
goto out;
}
}
+
+ if (cam_periph_acquire(periph) != CAM_REQ_CMP) {
+ xpt_print(periph->path, "%s: lost periph during "
+ "registration!\n", __func__);
+ cam_periph_lock(periph);
+
+ return (CAM_REQ_CMP_ERR);
+ }
+
enc->enc_dev = make_dev(&enc_cdevsw, periph->unit_number,
UID_ROOT, GID_OPERATOR, 0600, "%s%d",
periph->periph_name, periph->unit_number);
+
cam_periph_lock(periph);
enc->enc_dev->si_drv1 = periph;
Modified: user/ae/bootcode/sys/cam/scsi/scsi_pass.c
==============================================================================
--- user/ae/bootcode/sys/cam/scsi/scsi_pass.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/cam/scsi/scsi_pass.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -55,7 +55,8 @@ __FBSDID("$FreeBSD$");
typedef enum {
PASS_FLAG_OPEN = 0x01,
PASS_FLAG_LOCKED = 0x02,
- PASS_FLAG_INVALID = 0x04
+ PASS_FLAG_INVALID = 0x04,
+ PASS_FLAG_INITIAL_PHYSPATH = 0x08
} pass_flags;
typedef enum {
@@ -133,7 +134,18 @@ passinit(void)
printf("pass: Failed to attach master async callback "
"due to status 0x%x!\n", status);
}
-
+
+}
+
+static void
+passdevgonecb(void *arg)
+{
+ struct cam_periph *periph;
+
+ periph = (struct cam_periph *)arg;
+
+ xpt_print(periph->path, "%s: devfs entry is gone\n", __func__);
+ cam_periph_release(periph);
}
static void
@@ -151,6 +163,12 @@ passoninvalidate(struct cam_periph *peri
softc->flags |= PASS_FLAG_INVALID;
/*
+ * Tell devfs this device has gone away, and ask for a callback
+ * when it has cleaned up its state.
+ */
+ destroy_dev_sched_cb(softc->dev, passdevgonecb, periph);
+
+ /*
* XXX Return all queued I/O with ENXIO.
* XXX Handle any transactions queued to the card
* with XPT_ABORT_CCB.
@@ -176,11 +194,6 @@ passcleanup(struct cam_periph *periph)
cam_periph_unlock(periph);
taskqueue_drain(taskqueue_thread, &softc->add_physpath_task);
- /*
- * passcleanup() is indirectly a d_close method via passclose,
- * so using destroy_dev(9) directly can result in deadlock.
- */
- destroy_dev_sched(softc->dev);
cam_periph_lock(periph);
free(softc, M_DEVBUF);
@@ -199,6 +212,12 @@ pass_add_physpath(void *context, int pen
*/
periph = context;
softc = periph->softc;
+ cam_periph_lock(periph);
+ if (periph->flags & CAM_PERIPH_INVALID) {
+ cam_periph_unlock(periph);
+ return;
+ }
+ cam_periph_unlock(periph);
physpath = malloc(MAXPATHLEN, M_DEVBUF, M_WAITOK);
if (xpt_getattr(physpath, MAXPATHLEN,
"GEOM::physpath", periph->path) == 0
@@ -208,6 +227,19 @@ pass_add_physpath(void *context, int pen
softc->dev, softc->alias_dev, physpath);
}
free(physpath, M_DEVBUF);
+
+ /*
+ * Now that we've made our alias, we no longer have to have a
+ * reference to the device.
+ */
+ cam_periph_lock(periph);
+ if ((softc->flags & PASS_FLAG_INITIAL_PHYSPATH) == 0) {
+ softc->flags |= PASS_FLAG_INITIAL_PHYSPATH;
+ cam_periph_unlock(periph);
+ dev_rel(softc->dev);
+ }
+ else
+ cam_periph_unlock(periph);
}
static void
@@ -281,12 +313,12 @@ passregister(struct cam_periph *periph,
cgd = (struct ccb_getdev *)arg;
if (periph == NULL) {
- printf("passregister: periph was NULL!!\n");
+ printf("%s: periph was NULL!!\n", __func__);
return(CAM_REQ_CMP_ERR);
}
if (cgd == NULL) {
- printf("passregister: no getdev CCB, can't register device\n");
+ printf("%s: no getdev CCB, can't register device\n", __func__);
return(CAM_REQ_CMP_ERR);
}
@@ -294,8 +326,8 @@ passregister(struct cam_periph *periph,
M_DEVBUF, M_NOWAIT);
if (softc == NULL) {
- printf("passregister: Unable to probe new device. "
- "Unable to allocate softc\n");
+ printf("%s: Unable to probe new device. "
+ "Unable to allocate softc\n", __func__);
return(CAM_REQ_CMP_ERR);
}
@@ -331,10 +363,31 @@ passregister(struct cam_periph *periph,
DEVSTAT_TYPE_PASS,
DEVSTAT_PRIORITY_PASS);
+ /*
+ * Acquire a reference to the periph before we create the devfs
+ * instance for it. We'll release this reference once the devfs
+ * instance has been freed.
+ */
+ if (cam_periph_acquire(periph) != CAM_REQ_CMP) {
+ xpt_print(periph->path, "%s: lost periph during "
+ "registration!\n", __func__);
+ mtx_lock(periph->sim->mtx);
+ return (CAM_REQ_CMP_ERR);
+ }
+
/* Register the device */
softc->dev = make_dev(&pass_cdevsw, periph->unit_number,
UID_ROOT, GID_OPERATOR, 0600, "%s%d",
periph->periph_name, periph->unit_number);
+
+ /*
+ * Now that we have made the devfs instance, hold a reference to it
+ * until the task queue has run to setup the physical path alias.
+ * That way devfs won't get rid of the device before we add our
+ * alias.
+ */
+ dev_ref(softc->dev);
+
mtx_lock(periph->sim->mtx);
softc->dev->si_drv1 = periph;
Modified: user/ae/bootcode/sys/dev/puc/puc_cfg.h
==============================================================================
--- user/ae/bootcode/sys/dev/puc/puc_cfg.h Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/dev/puc/puc_cfg.h Thu Jun 21 14:37:05 2012 (r237399)
@@ -79,7 +79,7 @@ struct puc_cfg {
int8_t ports;
int8_t rid; /* Rid of first port */
int8_t d_rid; /* Delta rid of next ports */
- int8_t d_ofs; /* Delta offset of next ports */
+ int16_t d_ofs; /* Delta offset of next ports */
puc_config_f *config_function;
};
Modified: user/ae/bootcode/sys/dev/puc/pucdata.c
==============================================================================
--- user/ae/bootcode/sys/dev/puc/pucdata.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/dev/puc/pucdata.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -507,6 +507,18 @@ const struct puc_cfg puc_pci_devices[] =
.config_function = puc_config_quatech
},
+ { 0x1393, 0x1024, 0xffff, 0,
+ "Moxa Technologies, Smartio CP-102E/PCIe",
+ DEFAULT_RCLK * 8,
+ PUC_PORT_2S, 0x14, 0, 0x200
+ },
+
+ { 0x1393, 0x1025, 0xffff, 0,
+ "Moxa Technologies, Smartio CP-102EL/PCIe",
+ DEFAULT_RCLK * 8,
+ PUC_PORT_2S, 0x14, 0, 0x200,
+ },
+
{ 0x1393, 0x1040, 0xffff, 0,
"Moxa Technologies, Smartio C104H/PCI",
DEFAULT_RCLK * 8,
@@ -550,6 +562,19 @@ const struct puc_cfg puc_pci_devices[] =
PUC_PORT_4S, 0x18, 0, 8,
},
+ { 0x1393, 0x1144, 0xffff, 0,
+ "Moxa Technologies, Smartio CP-114EL/PCIe",
+ DEFAULT_RCLK * 8,
+ PUC_PORT_4S, 0x14, 0, -1,
+ .config_function = puc_config_moxa
+ },
+
+ { 0x1393, 0x1182, 0xffff, 0,
+ "Moxa Technologies, Smartio CP-118EL-A/PCIe",
+ DEFAULT_RCLK * 8,
+ PUC_PORT_8S, 0x14, 0, 0x200,
+ },
+
{ 0x1393, 0x1680, 0xffff, 0,
"Moxa Technologies, C168H/PCI",
DEFAULT_RCLK * 8,
@@ -568,6 +593,12 @@ const struct puc_cfg puc_pci_devices[] =
PUC_PORT_8S, 0x18, 0, 8,
},
+ { 0x1393, 0x1683, 0xffff, 0,
+ "Moxa Technologies, Smartio CP-168EL-A/PCIe",
+ DEFAULT_RCLK * 8,
+ PUC_PORT_8S, 0x14, 0, 0x200,
+ },
+
{ 0x13a8, 0x0152, 0xffff, 0,
"Exar XR17C/D152",
DEFAULT_RCLK * 8,
@@ -1127,9 +1158,7 @@ static int
puc_config_moxa(struct puc_softc *sc, enum puc_cfg_cmd cmd, int port,
intptr_t *res)
{
- const struct puc_cfg *cfg = sc->sc_cfg;
-
- if (cmd == PUC_CFG_GET_OFS && cfg->device == 0x1045) {
+ if (cmd == PUC_CFG_GET_OFS) {
*res = ((port == 3) ? 7 : port) * 0x200;
return 0;
}
Modified: user/ae/bootcode/sys/dev/viawd/viawd.c
==============================================================================
--- user/ae/bootcode/sys/dev/viawd/viawd.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/dev/viawd/viawd.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -168,14 +168,18 @@ viawd_attach(device_t dev)
}
/* Allocate I/O register space. */
- sc->wd_rid = 0;
- sc->wd_res = bus_alloc_resource(dev, SYS_RES_MEMORY, &sc->wd_rid,
- pmbase, pmbase + VIAWD_MEM_LEN - 1, VIAWD_MEM_LEN,
+ sc->wd_rid = VIAWD_CONFIG_BASE;
+ sc->wd_res = bus_alloc_resource_any(sb_dev, SYS_RES_MEMORY, &sc->wd_rid,
RF_ACTIVE | RF_SHAREABLE);
if (sc->wd_res == NULL) {
device_printf(dev, "Unable to map watchdog memory\n");
goto fail;
}
+ if (rman_get_size(sc->wd_res) < VIAWD_MEM_LEN) {
+ device_printf(dev, "Bad size for watchdog memory: %#x\n",
+ (unsigned)rman_get_size(sc->wd_res));
+ goto fail;
+ }
/* Check if watchdog fired last boot. */
reg = viawd_read_4(sc, VIAWD_MEM_CTRL);
@@ -192,7 +196,7 @@ viawd_attach(device_t dev)
return (0);
fail:
if (sc->wd_res != NULL)
- bus_release_resource(dev, SYS_RES_MEMORY,
+ bus_release_resource(sb_dev, SYS_RES_MEMORY,
sc->wd_rid, sc->wd_res);
return (ENXIO);
}
@@ -224,7 +228,7 @@ viawd_detach(device_t dev)
}
if (sc->wd_res != NULL)
- bus_release_resource(sc->dev, SYS_RES_MEMORY,
+ bus_release_resource(sc->sb_dev, SYS_RES_MEMORY,
sc->wd_rid, sc->wd_res);
return (0);
Modified: user/ae/bootcode/sys/dev/xen/balloon/balloon.c
==============================================================================
--- user/ae/bootcode/sys/dev/xen/balloon/balloon.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/dev/xen/balloon/balloon.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -436,6 +436,9 @@ balloon_init_watcher(void *arg)
{
int err;
+ if (!is_running_on_xen())
+ return;
+
err = xs_register_watch(&target_watch);
if (err)
printf("Failed to set balloon watcher\n");
Modified: user/ae/bootcode/sys/fs/nfsclient/nfs_clbio.c
==============================================================================
--- user/ae/bootcode/sys/fs/nfsclient/nfs_clbio.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/fs/nfsclient/nfs_clbio.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -722,7 +722,7 @@ ncl_bioread(struct vnode *vp, struct uio
};
if (n > 0) {
- error = uiomove(bp->b_data + on, (int)n, uio);
+ error = vn_io_fault_uiomove(bp->b_data + on, (int)n, uio);
}
if (vp->v_type == VLNK)
n = 0;
@@ -1203,7 +1203,7 @@ again:
}
local_resid = uio->uio_resid;
- error = uiomove((char *)bp->b_data + on, n, uio);
+ error = vn_io_fault_uiomove((char *)bp->b_data + on, n, uio);
if (error != 0 && !bp_cached) {
/*
Modified: user/ae/bootcode/sys/fs/nfsclient/nfs_clvfsops.c
==============================================================================
--- user/ae/bootcode/sys/fs/nfsclient/nfs_clvfsops.c Thu Jun 21 14:35:46 2012 (r237398)
+++ user/ae/bootcode/sys/fs/nfsclient/nfs_clvfsops.c Thu Jun 21 14:37:05 2012 (r237399)
@@ -1136,7 +1136,8 @@ nfs_mount(struct mount *mp)
out:
if (!error) {
MNT_ILOCK(mp);
- mp->mnt_kern_flag |= (MNTK_MPSAFE|MNTK_LOOKUP_SHARED);
+ mp->mnt_kern_flag |= MNTK_MPSAFE | MNTK_LOOKUP_SHARED |
+ MNTK_NO_IOPF;
MNT_IUNLOCK(mp);
}
return (error);
Modified: user/ae/bootcode/sys/kern/vfs_vnops.c
==============================================================================
--- user/ae/bootcode/sys/kern/vfs_vnops.c Thu Jun 21 14:35:46 2012 (r237398)
*** DIFF OUTPUT TRUNCATED AT 1000 LINES ***
More information about the svn-src-user
mailing list