- Timestamp:
- Oct 29, 2017 12:05:06 PM (8 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/kmk/kmkbuiltin/install.c
r3109 r3112 50 50 #ifndef _MSC_VER 51 51 # include <sys/param.h> 52 # ifdef USE_MMAP53 # include <sys/mman.h>54 # endif55 52 # if !defined(__HAIKU__) && !defined(__gnu_hurd__) 56 53 # include <sys/mount.h> … … 161 158 static u_long numeric_id(const char *, const char *); 162 159 static int strip(const char *); 163 #ifdef USE_MMAP164 static int trymmap(int);165 #endif166 160 static int usage(FILE *); 167 161 static char *last_slash(const char *); … … 782 776 int to_fd, const char *to_name __unused, size_t to_len) 783 777 { 784 char *p, *q; 778 char buf1[MAXBSIZE]; 779 char buf2[MAXBSIZE]; 780 int n1, n2; 785 781 int rv; 786 int done_compare; 787 788 rv = 0; 782 789 783 if (from_len != to_len) 790 784 return 1; 791 785 792 786 if (from_len <= MAX_CMP_SIZE) { 793 #ifdef USE_MMAP 794 done_compare = 0; 795 if (trymmap(from_fd) && trymmap(to_fd)) { 796 p = mmap(NULL, from_len, PROT_READ, MAP_SHARED, from_fd, (off_t)0); 797 if (p == (char *)MAP_FAILED) 798 goto out; 799 q = mmap(NULL, from_len, PROT_READ, MAP_SHARED, to_fd, (off_t)0); 800 if (q == (char *)MAP_FAILED) { 801 munmap(p, from_len); 802 goto out; 803 } 804 805 rv = memcmp(p, q, from_len); 806 munmap(p, from_len); 807 munmap(q, from_len); 808 done_compare = 1; 809 } 810 out: 811 #else 812 (void)p; (void)q; 813 done_compare = 0; 814 #endif 815 if (!done_compare) { 816 char buf1[MAXBSIZE]; 817 char buf2[MAXBSIZE]; 818 int n1, n2; 819 820 rv = 0; 821 lseek(from_fd, 0, SEEK_SET); 822 lseek(to_fd, 0, SEEK_SET); 823 while (rv == 0) { 824 n1 = read(from_fd, buf1, sizeof(buf1)); 825 if (n1 == 0) 826 break; /* EOF */ 827 else if (n1 > 0) { 828 n2 = read(to_fd, buf2, n1); 829 if (n2 == n1) 830 rv = memcmp(buf1, buf2, n1); 831 else 832 rv = 1; /* out of sync */ 833 } else 834 rv = 1; /* read failure */ 835 } 836 lseek(from_fd, 0, SEEK_SET); 837 lseek(to_fd, 0, SEEK_SET); 838 } 787 rv = 0; 788 lseek(from_fd, 0, SEEK_SET); 789 lseek(to_fd, 0, SEEK_SET); 790 while (rv == 0) { 791 n1 = read(from_fd, buf1, sizeof(buf1)); 792 if (n1 == 0) 793 break; /* EOF */ 794 else if (n1 > 0) { 795 n2 = read(to_fd, buf2, n1); 796 if (n2 == n1) 797 rv = memcmp(buf1, buf2, n1); 798 else 799 rv = 1; /* out of sync */ 800 } else 801 rv = 1; /* read failure */ 802 } 803 lseek(from_fd, 0, SEEK_SET); 804 lseek(to_fd, 0, SEEK_SET); 839 805 } else 840 806 rv = 1; /* don't bother in this case */ … … 923 889 int nr, nw; 924 890 int serrno; 925 char *p, buf[MAXBSIZE]; 926 int done_copy; 891 char buf[MAXBSIZE]; 892 893 (void)size; 927 894 928 895 /* Rewind file descriptors. */ … … 932 899 return err(EX_OSERR, "lseek: %s", to_name); 933 900 934 /* 935 * Mmap and write if less than 8M (the limit is so we don't totally 936 * trash memory on big files. This is really a minor hack, but it 937 * wins some CPU back. 938 */ 939 done_copy = 0; 940 #ifdef USE_MMAP 941 if (size <= 8 * 1048576 && trymmap(from_fd) && 942 (p = mmap(NULL, (size_t)size, PROT_READ, MAP_SHARED, 943 from_fd, (off_t)0)) != (char *)MAP_FAILED) { 944 if ((nw = write(to_fd, p, size)) != size) { 901 while ((nr = read(from_fd, buf, sizeof(buf))) > 0) 902 if ((nw = write(to_fd, buf, nr)) != nr) { 945 903 serrno = errno; 946 904 (void)unlink(to_name); 947 905 errno = nw > 0 ? EIO : serrno; 948 err(EX_OSERR, "%s", to_name); 949 } 950 done_copy = 1; 951 } 952 #else 953 (void)p; (void)size; 954 #endif 955 if (!done_copy) { 956 while ((nr = read(from_fd, buf, sizeof(buf))) > 0) 957 if ((nw = write(to_fd, buf, nr)) != nr) { 958 serrno = errno; 959 (void)unlink(to_name); 960 errno = nw > 0 ? EIO : serrno; 961 return err(EX_OSERR, "%s", to_name); 962 } 963 if (nr != 0) { 964 serrno = errno; 965 (void)unlink(to_name); 966 errno = serrno; 967 return err(EX_OSERR, "%s", from_name); 968 } 906 return err(EX_OSERR, "%s", to_name); 907 } 908 if (nr != 0) { 909 serrno = errno; 910 (void)unlink(to_name); 911 errno = serrno; 912 return err(EX_OSERR, "%s", from_name); 969 913 } 970 914 return EX_OK; … … 1076 1020 } 1077 1021 1078 #ifdef USE_MMAP1079 /*1080 * trymmap --1081 * return true (1) if mmap should be tried, false (0) if not.1082 */1083 static int1084 trymmap(int fd)1085 {1086 /*1087 * The ifdef is for bootstrapping - f_fstypename doesn't exist in1088 * pre-Lite2-merge systems.1089 */1090 #ifdef MFSNAMELEN1091 struct statfs stfs;1092 1093 if (nommap || fstatfs(fd, &stfs) != 0)1094 return (0);1095 if (strcmp(stfs.f_fstypename, "ufs") == 0 ||1096 strcmp(stfs.f_fstypename, "cd9660") == 0)1097 return (1);1098 #endif1099 return (0);1100 }1101 #endif1102 1103 1022 /* figures out where the last slash or colon is. */ 1104 1023 static char *
Note:
See TracChangeset
for help on using the changeset viewer.