sysv_msg.c (164368) | sysv_msg.c (165403) |
---|---|
1/*- 2 * Implementation of SVID messages 3 * 4 * Author: Daniel Boulet 5 * 6 * Copyright 1993 Daniel Boulet and RTMX Inc. 7 * 8 * This system call was implemented by Daniel Boulet under contract from RTMX. --- 34 unchanged lines hidden (view full) --- 43 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 44 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 45 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 46 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 47 * SUCH DAMAGE. 48 */ 49 50#include <sys/cdefs.h> | 1/*- 2 * Implementation of SVID messages 3 * 4 * Author: Daniel Boulet 5 * 6 * Copyright 1993 Daniel Boulet and RTMX Inc. 7 * 8 * This system call was implemented by Daniel Boulet under contract from RTMX. --- 34 unchanged lines hidden (view full) --- 43 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 44 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 45 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 46 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 47 * SUCH DAMAGE. 48 */ 49 50#include <sys/cdefs.h> |
51__FBSDID("$FreeBSD: head/sys/kern/sysv_msg.c 164368 2006-11-17 20:43:01Z jkim $"); | 51__FBSDID("$FreeBSD: head/sys/kern/sysv_msg.c 165403 2006-12-20 19:26:30Z jkim $"); |
52 53#include "opt_sysvipc.h" 54#include "opt_mac.h" 55 56#include <sys/param.h> 57#include <sys/systm.h> 58#include <sys/sysproto.h> 59#include <sys/kernel.h> --- 331 unchanged lines hidden (view full) --- 391 struct thread *td; 392 register struct msgctl_args *uap; 393{ 394 int msqid = uap->msqid; 395 int cmd = uap->cmd; 396 struct msqid_ds msqbuf; 397 int error; 398 | 52 53#include "opt_sysvipc.h" 54#include "opt_mac.h" 55 56#include <sys/param.h> 57#include <sys/systm.h> 58#include <sys/sysproto.h> 59#include <sys/kernel.h> --- 331 unchanged lines hidden (view full) --- 391 struct thread *td; 392 register struct msgctl_args *uap; 393{ 394 int msqid = uap->msqid; 395 int cmd = uap->cmd; 396 struct msqid_ds msqbuf; 397 int error; 398 |
399 DPRINTF(("call to msgctl(%d, %d, 0x%x)\n", msqid, cmd, uap->buf)); | 399 DPRINTF(("call to msgctl(%d, %d, %p)\n", msqid, cmd, uap->buf)); |
400 if (cmd == IPC_SET && 401 (error = copyin(uap->buf, &msqbuf, sizeof(msqbuf))) != 0) 402 return (error); 403 error = kern_msgctl(td, msqid, cmd, &msqbuf); 404 if (cmd == IPC_STAT && error == 0) 405 error = copyout(&msqbuf, uap->buf, sizeof(struct msqid_ds)); 406 return (error); 407} --- 258 unchanged lines hidden (view full) --- 666struct msgsnd_args { 667 int msqid; 668 const void *msgp; 669 size_t msgsz; 670 int msgflg; 671}; 672#endif 673 | 400 if (cmd == IPC_SET && 401 (error = copyin(uap->buf, &msqbuf, sizeof(msqbuf))) != 0) 402 return (error); 403 error = kern_msgctl(td, msqid, cmd, &msqbuf); 404 if (cmd == IPC_STAT && error == 0) 405 error = copyout(&msqbuf, uap->buf, sizeof(struct msqid_ds)); 406 return (error); 407} --- 258 unchanged lines hidden (view full) --- 666struct msgsnd_args { 667 int msqid; 668 const void *msgp; 669 size_t msgsz; 670 int msgflg; 671}; 672#endif 673 |
674/* 675 * MPSAFE 676 */ | |
677int | 674int |
678msgsnd(td, uap) | 675kern_msgsnd(td, msqid, msgp, msgsz, msgflg, mtype) |
679 struct thread *td; | 676 struct thread *td; |
680 register struct msgsnd_args *uap; | 677 int msqid; 678 const void *msgp; /* XXX msgp is actually mtext. */ 679 size_t msgsz; 680 int msgflg; 681 long mtype; |
681{ | 682{ |
682 int msqid = uap->msqid; 683 const void *user_msgp = uap->msgp; 684 size_t msgsz = uap->msgsz; 685 int msgflg = uap->msgflg; 686 int segs_needed, error = 0; | 683 int msqix, segs_needed, error = 0; |
687 register struct msqid_kernel *msqkptr; 688 register struct msg *msghdr; 689 short next; 690 | 684 register struct msqid_kernel *msqkptr; 685 register struct msg *msghdr; 686 short next; 687 |
691 DPRINTF(("call to msgsnd(%d, 0x%x, %d, %d)\n", msqid, user_msgp, msgsz, 692 msgflg)); | |
693 if (!jail_sysvipc_allowed && jailed(td->td_ucred)) 694 return (ENOSYS); 695 696 mtx_lock(&msq_mtx); | 688 if (!jail_sysvipc_allowed && jailed(td->td_ucred)) 689 return (ENOSYS); 690 691 mtx_lock(&msq_mtx); |
697 msqid = IPCID_TO_IX(msqid); | 692 msqix = IPCID_TO_IX(msqid); |
698 | 693 |
699 if (msqid < 0 || msqid >= msginfo.msgmni) { 700 DPRINTF(("msqid (%d) out of range (0<=msqid<%d)\n", msqid, | 694 if (msqix < 0 || msqix >= msginfo.msgmni) { 695 DPRINTF(("msqid (%d) out of range (0<=msqid<%d)\n", msqix, |
701 msginfo.msgmni)); 702 error = EINVAL; 703 goto done2; 704 } 705 | 696 msginfo.msgmni)); 697 error = EINVAL; 698 goto done2; 699 } 700 |
706 msqkptr = &msqids[msqid]; | 701 msqkptr = &msqids[msqix]; |
707 if (msqkptr->u.msg_qbytes == 0) { 708 DPRINTF(("no such message queue id\n")); 709 error = EINVAL; 710 goto done2; 711 } | 702 if (msqkptr->u.msg_qbytes == 0) { 703 DPRINTF(("no such message queue id\n")); 704 error = EINVAL; 705 goto done2; 706 } |
712 if (msqkptr->u.msg_perm.seq != IPCID_TO_SEQ(uap->msqid)) { | 707 if (msqkptr->u.msg_perm.seq != IPCID_TO_SEQ(msqid)) { |
713 DPRINTF(("wrong sequence number\n")); 714 error = EINVAL; 715 goto done2; 716 } 717 718 if ((error = ipcperm(td, &msqkptr->u.msg_perm, IPC_W))) { 719 DPRINTF(("requester doesn't have write access\n")); 720 goto done2; 721 } 722 723#ifdef MAC 724 error = mac_check_sysv_msqsnd(td->td_ucred, msqkptr); 725 if (error != 0) 726 goto done2; 727#endif 728 729 segs_needed = (msgsz + msginfo.msgssz - 1) / msginfo.msgssz; | 708 DPRINTF(("wrong sequence number\n")); 709 error = EINVAL; 710 goto done2; 711 } 712 713 if ((error = ipcperm(td, &msqkptr->u.msg_perm, IPC_W))) { 714 DPRINTF(("requester doesn't have write access\n")); 715 goto done2; 716 } 717 718#ifdef MAC 719 error = mac_check_sysv_msqsnd(td->td_ucred, msqkptr); 720 if (error != 0) 721 goto done2; 722#endif 723 724 segs_needed = (msgsz + msginfo.msgssz - 1) / msginfo.msgssz; |
730 DPRINTF(("msgsz=%d, msgssz=%d, segs_needed=%d\n", msgsz, msginfo.msgssz, 731 segs_needed)); | 725 DPRINTF(("msgsz=%zu, msgssz=%d, segs_needed=%d\n", msgsz, 726 msginfo.msgssz, segs_needed)); |
732 for (;;) { 733 int need_more_resources = 0; 734 735 /* 736 * check msgsz 737 * (inside this loop in case msg_qbytes changes while we sleep) 738 */ 739 --- 98 unchanged lines hidden (view full) --- 838 /* 839 * Allocate a message header 840 */ 841 842 msghdr = free_msghdrs; 843 free_msghdrs = msghdr->msg_next; 844 msghdr->msg_spot = -1; 845 msghdr->msg_ts = msgsz; | 727 for (;;) { 728 int need_more_resources = 0; 729 730 /* 731 * check msgsz 732 * (inside this loop in case msg_qbytes changes while we sleep) 733 */ 734 --- 98 unchanged lines hidden (view full) --- 833 /* 834 * Allocate a message header 835 */ 836 837 msghdr = free_msghdrs; 838 free_msghdrs = msghdr->msg_next; 839 msghdr->msg_spot = -1; 840 msghdr->msg_ts = msgsz; |
841 msghdr->msg_type = mtype; |
|
846#ifdef MAC 847 /* 848 * XXXMAC: Should the mac_check_sysv_msgmsq check follow here 849 * immediately? Or, should it be checked just before the msg is 850 * enqueued in the msgq (as it is done now)? 851 */ 852 mac_create_sysv_msgmsg(td->td_ucred, msqkptr, msghdr); 853#endif --- 16 unchanged lines hidden (view full) --- 870 free_msgmaps = msgmaps[next].next; 871 nfree_msgmaps--; 872 msgmaps[next].next = msghdr->msg_spot; 873 msghdr->msg_spot = next; 874 segs_needed--; 875 } 876 877 /* | 842#ifdef MAC 843 /* 844 * XXXMAC: Should the mac_check_sysv_msgmsq check follow here 845 * immediately? Or, should it be checked just before the msg is 846 * enqueued in the msgq (as it is done now)? 847 */ 848 mac_create_sysv_msgmsg(td->td_ucred, msqkptr, msghdr); 849#endif --- 16 unchanged lines hidden (view full) --- 866 free_msgmaps = msgmaps[next].next; 867 nfree_msgmaps--; 868 msgmaps[next].next = msghdr->msg_spot; 869 msghdr->msg_spot = next; 870 segs_needed--; 871 } 872 873 /* |
878 * Copy in the message type 879 */ 880 881 mtx_unlock(&msq_mtx); 882 if ((error = copyin(user_msgp, &msghdr->msg_type, 883 sizeof(msghdr->msg_type))) != 0) { 884 mtx_lock(&msq_mtx); 885 DPRINTF(("error %d copying the message type\n", error)); 886 msg_freehdr(msghdr); 887 msqkptr->u.msg_perm.mode &= ~MSG_LOCKED; 888 wakeup(msqkptr); 889 goto done2; 890 } 891 mtx_lock(&msq_mtx); 892 user_msgp = (const char *)user_msgp + sizeof(msghdr->msg_type); 893 894 /* | |
895 * Validate the message type 896 */ 897 898 if (msghdr->msg_type < 1) { 899 msg_freehdr(msghdr); 900 msqkptr->u.msg_perm.mode &= ~MSG_LOCKED; 901 wakeup(msqkptr); | 874 * Validate the message type 875 */ 876 877 if (msghdr->msg_type < 1) { 878 msg_freehdr(msghdr); 879 msqkptr->u.msg_perm.mode &= ~MSG_LOCKED; 880 wakeup(msqkptr); |
902 DPRINTF(("mtype (%d) < 1\n", msghdr->msg_type)); | 881 DPRINTF(("mtype (%ld) < 1\n", msghdr->msg_type)); |
903 error = EINVAL; 904 goto done2; 905 } 906 907 /* 908 * Copy in the message body 909 */ 910 --- 4 unchanged lines hidden (view full) --- 915 tlen = msginfo.msgssz; 916 else 917 tlen = msgsz; 918 if (next <= -1) 919 panic("next too low #2"); 920 if (next >= msginfo.msgseg) 921 panic("next out of range #2"); 922 mtx_unlock(&msq_mtx); | 882 error = EINVAL; 883 goto done2; 884 } 885 886 /* 887 * Copy in the message body 888 */ 889 --- 4 unchanged lines hidden (view full) --- 894 tlen = msginfo.msgssz; 895 else 896 tlen = msgsz; 897 if (next <= -1) 898 panic("next too low #2"); 899 if (next >= msginfo.msgseg) 900 panic("next out of range #2"); 901 mtx_unlock(&msq_mtx); |
923 if ((error = copyin(user_msgp, &msgpool[next * msginfo.msgssz], | 902 if ((error = copyin(msgp, &msgpool[next * msginfo.msgssz], |
924 tlen)) != 0) { 925 mtx_lock(&msq_mtx); 926 DPRINTF(("error %d copying in message segment\n", 927 error)); 928 msg_freehdr(msghdr); 929 msqkptr->u.msg_perm.mode &= ~MSG_LOCKED; 930 wakeup(msqkptr); 931 goto done2; 932 } 933 mtx_lock(&msq_mtx); 934 msgsz -= tlen; | 903 tlen)) != 0) { 904 mtx_lock(&msq_mtx); 905 DPRINTF(("error %d copying in message segment\n", 906 error)); 907 msg_freehdr(msghdr); 908 msqkptr->u.msg_perm.mode &= ~MSG_LOCKED; 909 wakeup(msqkptr); 910 goto done2; 911 } 912 mtx_lock(&msq_mtx); 913 msgsz -= tlen; |
935 user_msgp = (const char *)user_msgp + tlen; | 914 msgp = (const char *)msgp + tlen; |
936 next = msgmaps[next].next; 937 } 938 if (next != -1) 939 panic("didn't use all the msg segments"); 940 941 /* 942 * We've got the message. Unlock the msqid_ds. 943 */ --- 50 unchanged lines hidden (view full) --- 994 995 wakeup(msqkptr); 996 td->td_retval[0] = 0; 997done2: 998 mtx_unlock(&msq_mtx); 999 return (error); 1000} 1001 | 915 next = msgmaps[next].next; 916 } 917 if (next != -1) 918 panic("didn't use all the msg segments"); 919 920 /* 921 * We've got the message. Unlock the msqid_ds. 922 */ --- 50 unchanged lines hidden (view full) --- 973 974 wakeup(msqkptr); 975 td->td_retval[0] = 0; 976done2: 977 mtx_unlock(&msq_mtx); 978 return (error); 979} 980 |
981/* 982 * MPSAFE 983 */ 984int 985msgsnd(td, uap) 986 struct thread *td; 987 register struct msgsnd_args *uap; 988{ 989 int error; 990 long mtype; 991 992 DPRINTF(("call to msgsnd(%d, %p, %zu, %d)\n", uap->msqid, uap->msgp, 993 uap->msgsz, uap->msgflg)); 994 995 if ((error = copyin(uap->msgp, &mtype, sizeof(mtype))) != 0) { 996 DPRINTF(("error %d copying the message type\n", error)); 997 return (error); 998 } 999 return (kern_msgsnd(td, uap->msqid, 1000 (const char *)uap->msgp + sizeof(mtype), 1001 uap->msgsz, uap->msgflg, mtype)); 1002} 1003 |
|
1002#ifndef _SYS_SYSPROTO_H_ 1003struct msgrcv_args { 1004 int msqid; 1005 void *msgp; 1006 size_t msgsz; 1007 long msgtyp; 1008 int msgflg; 1009}; 1010#endif 1011 | 1004#ifndef _SYS_SYSPROTO_H_ 1005struct msgrcv_args { 1006 int msqid; 1007 void *msgp; 1008 size_t msgsz; 1009 long msgtyp; 1010 int msgflg; 1011}; 1012#endif 1013 |
1012/* 1013 * MPSAFE 1014 */ | |
1015int | 1014int |
1016msgrcv(td, uap) | 1015kern_msgrcv(td, msqid, msgp, msgsz, msgtyp, msgflg, mtype) |
1017 struct thread *td; | 1016 struct thread *td; |
1018 register struct msgrcv_args *uap; | 1017 int msqid; 1018 void *msgp; /* XXX msgp is actually mtext. */ 1019 size_t msgsz; 1020 long msgtyp; 1021 int msgflg; 1022 long *mtype; |
1019{ | 1023{ |
1020 int msqid = uap->msqid; 1021 void *user_msgp = uap->msgp; 1022 size_t msgsz = uap->msgsz; 1023 long msgtyp = uap->msgtyp; 1024 int msgflg = uap->msgflg; | |
1025 size_t len; 1026 register struct msqid_kernel *msqkptr; 1027 register struct msg *msghdr; | 1024 size_t len; 1025 register struct msqid_kernel *msqkptr; 1026 register struct msg *msghdr; |
1028 int error = 0; | 1027 int msqix, error = 0; |
1029 short next; 1030 | 1028 short next; 1029 |
1031 DPRINTF(("call to msgrcv(%d, 0x%x, %d, %ld, %d)\n", msqid, user_msgp, 1032 msgsz, msgtyp, msgflg)); 1033 | |
1034 if (!jail_sysvipc_allowed && jailed(td->td_ucred)) 1035 return (ENOSYS); 1036 | 1030 if (!jail_sysvipc_allowed && jailed(td->td_ucred)) 1031 return (ENOSYS); 1032 |
1037 msqid = IPCID_TO_IX(msqid); | 1033 msqix = IPCID_TO_IX(msqid); |
1038 | 1034 |
1039 if (msqid < 0 || msqid >= msginfo.msgmni) { 1040 DPRINTF(("msqid (%d) out of range (0<=msqid<%d)\n", msqid, | 1035 if (msqix < 0 || msqix >= msginfo.msgmni) { 1036 DPRINTF(("msqid (%d) out of range (0<=msqid<%d)\n", msqix, |
1041 msginfo.msgmni)); 1042 return (EINVAL); 1043 } 1044 | 1037 msginfo.msgmni)); 1038 return (EINVAL); 1039 } 1040 |
1045 msqkptr = &msqids[msqid]; | 1041 msqkptr = &msqids[msqix]; |
1046 mtx_lock(&msq_mtx); 1047 if (msqkptr->u.msg_qbytes == 0) { 1048 DPRINTF(("no such message queue id\n")); 1049 error = EINVAL; 1050 goto done2; 1051 } | 1042 mtx_lock(&msq_mtx); 1043 if (msqkptr->u.msg_qbytes == 0) { 1044 DPRINTF(("no such message queue id\n")); 1045 error = EINVAL; 1046 goto done2; 1047 } |
1052 if (msqkptr->u.msg_perm.seq != IPCID_TO_SEQ(uap->msqid)) { | 1048 if (msqkptr->u.msg_perm.seq != IPCID_TO_SEQ(msqid)) { |
1053 DPRINTF(("wrong sequence number\n")); 1054 error = EINVAL; 1055 goto done2; 1056 } 1057 1058 if ((error = ipcperm(td, &msqkptr->u.msg_perm, IPC_R))) { 1059 DPRINTF(("requester doesn't have read access\n")); 1060 goto done2; --- 8 unchanged lines hidden (view full) --- 1069 msghdr = NULL; 1070 while (msghdr == NULL) { 1071 if (msgtyp == 0) { 1072 msghdr = msqkptr->u.msg_first; 1073 if (msghdr != NULL) { 1074 if (msgsz < msghdr->msg_ts && 1075 (msgflg & MSG_NOERROR) == 0) { 1076 DPRINTF(("first message on the queue " | 1049 DPRINTF(("wrong sequence number\n")); 1050 error = EINVAL; 1051 goto done2; 1052 } 1053 1054 if ((error = ipcperm(td, &msqkptr->u.msg_perm, IPC_R))) { 1055 DPRINTF(("requester doesn't have read access\n")); 1056 goto done2; --- 8 unchanged lines hidden (view full) --- 1065 msghdr = NULL; 1066 while (msghdr == NULL) { 1067 if (msgtyp == 0) { 1068 msghdr = msqkptr->u.msg_first; 1069 if (msghdr != NULL) { 1070 if (msgsz < msghdr->msg_ts && 1071 (msgflg & MSG_NOERROR) == 0) { 1072 DPRINTF(("first message on the queue " |
1077 "is too big (want %d, got %d)\n", | 1073 "is too big (want %zu, got %d)\n", |
1078 msgsz, msghdr->msg_ts)); 1079 error = E2BIG; 1080 goto done2; 1081 } 1082#ifdef MAC 1083 error = mac_check_sysv_msgrcv(td->td_ucred, 1084 msghdr); 1085 if (error != 0) --- 21 unchanged lines hidden (view full) --- 1107 * the absolute value of a negative msgtyp? 1108 * Note that the second half of this test can 1109 * NEVER be true if msgtyp is positive since 1110 * msg_type is always positive! 1111 */ 1112 1113 if (msgtyp == msghdr->msg_type || 1114 msghdr->msg_type <= -msgtyp) { | 1074 msgsz, msghdr->msg_ts)); 1075 error = E2BIG; 1076 goto done2; 1077 } 1078#ifdef MAC 1079 error = mac_check_sysv_msgrcv(td->td_ucred, 1080 msghdr); 1081 if (error != 0) --- 21 unchanged lines hidden (view full) --- 1103 * the absolute value of a negative msgtyp? 1104 * Note that the second half of this test can 1105 * NEVER be true if msgtyp is positive since 1106 * msg_type is always positive! 1107 */ 1108 1109 if (msgtyp == msghdr->msg_type || 1110 msghdr->msg_type <= -msgtyp) { |
1115 DPRINTF(("found message type %d, " 1116 "requested %d\n", | 1111 DPRINTF(("found message type %ld, " 1112 "requested %ld\n", |
1117 msghdr->msg_type, msgtyp)); 1118 if (msgsz < msghdr->msg_ts && 1119 (msgflg & MSG_NOERROR) == 0) { 1120 DPRINTF(("requested message " 1121 "on the queue is too big " | 1113 msghdr->msg_type, msgtyp)); 1114 if (msgsz < msghdr->msg_ts && 1115 (msgflg & MSG_NOERROR) == 0) { 1116 DPRINTF(("requested message " 1117 "on the queue is too big " |
1122 "(want %d, got %d)\n", | 1118 "(want %zu, got %hu)\n", |
1123 msgsz, msghdr->msg_ts)); 1124 error = E2BIG; 1125 goto done2; 1126 } 1127#ifdef MAC 1128 error = mac_check_sysv_msgrcv( 1129 td->td_ucred, msghdr); 1130 if (error != 0) --- 33 unchanged lines hidden (view full) --- 1164 if (msghdr != NULL) 1165 break; 1166 1167 /* 1168 * Hmph! No message found. Does the user want to wait? 1169 */ 1170 1171 if ((msgflg & IPC_NOWAIT) != 0) { | 1119 msgsz, msghdr->msg_ts)); 1120 error = E2BIG; 1121 goto done2; 1122 } 1123#ifdef MAC 1124 error = mac_check_sysv_msgrcv( 1125 td->td_ucred, msghdr); 1126 if (error != 0) --- 33 unchanged lines hidden (view full) --- 1160 if (msghdr != NULL) 1161 break; 1162 1163 /* 1164 * Hmph! No message found. Does the user want to wait? 1165 */ 1166 1167 if ((msgflg & IPC_NOWAIT) != 0) { |
1172 DPRINTF(("no appropriate message found (msgtyp=%d)\n", | 1168 DPRINTF(("no appropriate message found (msgtyp=%ld)\n", |
1173 msgtyp)); 1174 /* The SVID says to return ENOMSG. */ 1175 error = ENOMSG; 1176 goto done2; 1177 } 1178 1179 /* 1180 * Wait for something to happen --- 10 unchanged lines hidden (view full) --- 1191 goto done2; 1192 } 1193 1194 /* 1195 * Make sure that the msq queue still exists 1196 */ 1197 1198 if (msqkptr->u.msg_qbytes == 0 || | 1169 msgtyp)); 1170 /* The SVID says to return ENOMSG. */ 1171 error = ENOMSG; 1172 goto done2; 1173 } 1174 1175 /* 1176 * Wait for something to happen --- 10 unchanged lines hidden (view full) --- 1187 goto done2; 1188 } 1189 1190 /* 1191 * Make sure that the msq queue still exists 1192 */ 1193 1194 if (msqkptr->u.msg_qbytes == 0 || |
1199 msqkptr->u.msg_perm.seq != IPCID_TO_SEQ(uap->msqid)) { | 1195 msqkptr->u.msg_perm.seq != IPCID_TO_SEQ(msqid)) { |
1200 DPRINTF(("msqid deleted\n")); 1201 error = EIDRM; 1202 goto done2; 1203 } 1204 } 1205 1206 /* 1207 * Return the message to the user. --- 7 unchanged lines hidden (view full) --- 1215 msqkptr->u.msg_rtime = time_second; 1216 1217 /* 1218 * Make msgsz the actual amount that we'll be returning. 1219 * Note that this effectively truncates the message if it is too long 1220 * (since msgsz is never increased). 1221 */ 1222 | 1196 DPRINTF(("msqid deleted\n")); 1197 error = EIDRM; 1198 goto done2; 1199 } 1200 } 1201 1202 /* 1203 * Return the message to the user. --- 7 unchanged lines hidden (view full) --- 1211 msqkptr->u.msg_rtime = time_second; 1212 1213 /* 1214 * Make msgsz the actual amount that we'll be returning. 1215 * Note that this effectively truncates the message if it is too long 1216 * (since msgsz is never increased). 1217 */ 1218 |
1223 DPRINTF(("found a message, msgsz=%d, msg_ts=%d\n", msgsz, | 1219 DPRINTF(("found a message, msgsz=%zu, msg_ts=%hu\n", msgsz, |
1224 msghdr->msg_ts)); 1225 if (msgsz > msghdr->msg_ts) 1226 msgsz = msghdr->msg_ts; | 1220 msghdr->msg_ts)); 1221 if (msgsz > msghdr->msg_ts) 1222 msgsz = msghdr->msg_ts; |
1223 *mtype = msghdr->msg_type; |
|
1227 1228 /* | 1224 1225 /* |
1229 * Return the type to the user. 1230 */ 1231 1232 mtx_unlock(&msq_mtx); 1233 error = copyout(&(msghdr->msg_type), user_msgp, 1234 sizeof(msghdr->msg_type)); 1235 mtx_lock(&msq_mtx); 1236 if (error != 0) { 1237 DPRINTF(("error (%d) copying out message type\n", error)); 1238 msg_freehdr(msghdr); 1239 wakeup(msqkptr); 1240 goto done2; 1241 } 1242 user_msgp = (char *)user_msgp + sizeof(msghdr->msg_type); 1243 1244 /* | |
1245 * Return the segments to the user 1246 */ 1247 1248 next = msghdr->msg_spot; 1249 for (len = 0; len < msgsz; len += msginfo.msgssz) { 1250 size_t tlen; 1251 1252 if (msgsz - len > msginfo.msgssz) 1253 tlen = msginfo.msgssz; 1254 else 1255 tlen = msgsz - len; 1256 if (next <= -1) 1257 panic("next too low #3"); 1258 if (next >= msginfo.msgseg) 1259 panic("next out of range #3"); 1260 mtx_unlock(&msq_mtx); | 1226 * Return the segments to the user 1227 */ 1228 1229 next = msghdr->msg_spot; 1230 for (len = 0; len < msgsz; len += msginfo.msgssz) { 1231 size_t tlen; 1232 1233 if (msgsz - len > msginfo.msgssz) 1234 tlen = msginfo.msgssz; 1235 else 1236 tlen = msgsz - len; 1237 if (next <= -1) 1238 panic("next too low #3"); 1239 if (next >= msginfo.msgseg) 1240 panic("next out of range #3"); 1241 mtx_unlock(&msq_mtx); |
1261 error = copyout(&msgpool[next * msginfo.msgssz], 1262 user_msgp, tlen); | 1242 error = copyout(&msgpool[next * msginfo.msgssz], msgp, tlen); |
1263 mtx_lock(&msq_mtx); 1264 if (error != 0) { 1265 DPRINTF(("error (%d) copying out message segment\n", 1266 error)); 1267 msg_freehdr(msghdr); 1268 wakeup(msqkptr); 1269 goto done2; 1270 } | 1243 mtx_lock(&msq_mtx); 1244 if (error != 0) { 1245 DPRINTF(("error (%d) copying out message segment\n", 1246 error)); 1247 msg_freehdr(msghdr); 1248 wakeup(msqkptr); 1249 goto done2; 1250 } |
1271 user_msgp = (char *)user_msgp + tlen; | 1251 msgp = (char *)msgp + tlen; |
1272 next = msgmaps[next].next; 1273 } 1274 1275 /* 1276 * Done, return the actual number of bytes copied out. 1277 */ 1278 1279 msg_freehdr(msghdr); 1280 wakeup(msqkptr); 1281 td->td_retval[0] = msgsz; 1282done2: 1283 mtx_unlock(&msq_mtx); 1284 return (error); 1285} 1286 | 1252 next = msgmaps[next].next; 1253 } 1254 1255 /* 1256 * Done, return the actual number of bytes copied out. 1257 */ 1258 1259 msg_freehdr(msghdr); 1260 wakeup(msqkptr); 1261 td->td_retval[0] = msgsz; 1262done2: 1263 mtx_unlock(&msq_mtx); 1264 return (error); 1265} 1266 |
1267/* 1268 * MPSAFE 1269 */ 1270int 1271msgrcv(td, uap) 1272 struct thread *td; 1273 register struct msgrcv_args *uap; 1274{ 1275 int error; 1276 long mtype; 1277 1278 DPRINTF(("call to msgrcv(%d, %p, %zu, %ld, %d)\n", uap->msqid, 1279 uap->msgp, uap->msgsz, uap->msgtyp, uap->msgflg)); 1280 1281 if ((error = kern_msgrcv(td, uap->msqid, 1282 (char *)uap->msgp + sizeof(mtype), uap->msgsz, 1283 uap->msgtyp, uap->msgflg, &mtype)) != 0) 1284 return (error); 1285 if ((error = copyout(&mtype, uap->msgp, sizeof(mtype))) != 0) 1286 DPRINTF(("error %d copying the message type\n", error)); 1287 return (error); 1288} 1289 |
|
1287static int 1288sysctl_msqids(SYSCTL_HANDLER_ARGS) 1289{ 1290 1291 return (SYSCTL_OUT(req, msqids, 1292 sizeof(struct msqid_kernel) * msginfo.msgmni)); 1293} 1294 --- 14 unchanged lines hidden --- | 1290static int 1291sysctl_msqids(SYSCTL_HANDLER_ARGS) 1292{ 1293 1294 return (SYSCTL_OUT(req, msqids, 1295 sizeof(struct msqid_kernel) * msginfo.msgmni)); 1296} 1297 --- 14 unchanged lines hidden --- |