X-Original-To: alpine-user@lists.alpinelinux.org Received: from sdaoden.eu (sdaoden.eu [217.144.132.164]) by lists.alpinelinux.org (Postfix) with ESMTP id C3B3AF859C5 for ; Fri, 18 Jan 2019 23:00:13 +0000 (UTC) Received: by sdaoden.eu (Postfix, from userid 1000) id A77671604A; Sat, 19 Jan 2019 00:00:12 +0100 (CET) Date: Sat, 19 Jan 2019 00:00:12 +0100 From: Steffen Nurpmeso To: alpine-user@lists.alpinelinux.org Subject: Re: [alpine-user] Startup hangs (aports: sshd?) Message-ID: <20190118230012.3me-O%steffen@sdaoden.eu> In-Reply-To: <20190117140207.lqzvY%steffen@sdaoden.eu> References: <20190117140207.lqzvY%steffen@sdaoden.eu> Mail-Followup-To: alpine-user@lists.alpinelinux.org User-Agent: s-nail v14.9.11-149-g00aa3097 OpenPGP: id=EE19E1C1F2F7054F8D3954D8308964B51883A0DD; url=https://ftp.sdaoden.eu/steffen.asc; preference=signencrypt BlahBlahBlah: Any stupid boy can crush a beetle. But all the professors in the world can make no bugs. X-Mailinglist: alpine-user Precedence: list List-Id: Alpine Development List-Unsubscribe: List-Post: List-Help: List-Subscribe: Hello again. Steffen Nurpmeso wrote in <20190117140207.lqzvY%steffen@sdaoden.eu>: |After upgrading to [edge] i see a possibly endless hang upon |startup, which seems to be caused by PRNG init. I have seen the |AlpineLinux bug report from two years ago. I have seen hangs of |about one to two minutes on the VM since, hmm, not too long, maybe |two or three months?, and on the bare metal we do hang also about .. So what am i supposed to do, entirely switch to linux-virt on the VM? I mean, ok, i could do that, but for example on this laptop i have multiple installations, and can either boot them from within each other via qemu, as well as via refit. Anyway, i have written something that saves entropy in a file and fills it in via ioctl(2), the stuff goes #?0|essex:tmp$ ./zt save /tmp/t.dat - 3420 bits of entropy available at /dev/random - 2396 bits of entropy remain at /dev/random - 1024 bits / 115 bytes of entropy saved to /tmp/t.dat ... #?0|essex:/etc/init.d# /tmp/zt load /tmp/t.dat - 2631 bits of entropy available at /dev/random - 115 bytes / 1024 bits of entropy read from /tmp/t.dat - Entropy added - 2905 bits of entropy are at at /dev/random So call this two hour hack stupid, but i will use it. I will look out for linux-virt after the next kernel update. A nice weekend i wish. /*@ Save and load Linux (2.6.0+) entropy. *@ Synopsis: entropy-saver save [file] *@ Synopsis: entropy-saver load [file] *@ "file" defaults to a_RAND_FILE_STORE. * * Copyright (c) 2019 Steffen (Daode) Nurpmeso . * SPDX-License-Identifier: ISC * * Permission to use, copy, modify, and/or distribute this software for any * purpose with or without fee is hereby granted, provided that the above * copyright notice and this permission notice appear in all copies. * * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ /* Random device*/ #define a_RAND_DEV "/dev/random" /* Maximum number of bytes we handle (must be LT INT_MAX/8!) */ #define a_RAND_NO_BYTES 512 /* Default storage */ #define a_RAND_FILE_STORE "/var/lib/misc/random.dat" #include #include #include #include #include #include #include #include #include #include #include #if KERNEL_VERSION(2,6,0) >= LINUX_VERSION_CODE # error Linux kernel version and IOCTL usage incompatible. #endif static char const a_rand_file_store[] = a_RAND_FILE_STORE; int main(int argc, char **argv){ enum {a_LOAD, a_SAVE}; struct{ struct rand_pool_info rpi; char buf[a_RAND_NO_BYTES]; } x; char *rpibuf; /* To make C++ happy: rpi.buf is char[0] */ ssize_t len; char const *store; int rv, accu, randfd, storfd, iocarg; if(argc < 2 || argc > 3) goto jeuse; if(!strcmp(argv[1], "load")) accu = a_LOAD; else if(!strcmp(argv[1], "save")) accu = a_SAVE; else{ jeuse: fprintf(stderr, "Synopsis: entropy-saver save [storage-file]\n" "Synopsis: entropy-saver load [storage-file]\n" "\n" "storage-file defaults to " a_RAND_FILE_STORE "\n" "Exit: sysexits.h: EX_USAGE, EX_NOPERM, EX_IOERR, EX_TEMPFAIL\n"); rv = EX_USAGE; goto jleave; } randfd = open(a_RAND_DEV, (O_RDONLY | O_NONBLOCK)); if(randfd == -1){ accu = errno; fprintf(stderr, "Failed to open " a_RAND_DEV ": %s\n", strerror(accu)); rv = (accu == EACCES || accu == EPERM) ? EX_NOPERM : EX_IOERR; goto jleave; } store = (argv[2] != NULL) ? argv[2] : a_rand_file_store; storfd = open(store, (accu == a_LOAD ? O_RDONLY : O_WRONLY | O_CREAT | O_TRUNC), (S_IRUSR | S_IWUSR)); if(storfd == -1){ accu = errno; fprintf(stderr, "Failed to open %s: %s\n", store, strerror(accu)); rv = (accu == EACCES || accu == EPERM) ? EX_NOPERM : EX_IOERR; goto jerr1; } /* For at least statistics */ rv = ioctl(randfd, (int)RNDGETENTCNT, &iocarg); if(rv == -1){ fprintf(stderr, "Failed to query available entropy of " a_RAND_DEV ": %s\n", strerror(errno)); rv = EX_IOERR; goto jerr2; } x.rpi.entropy_count = iocarg; rpibuf = (char*)x.rpi.buf; if(accu == a_LOAD){ printf("- %d bits of entropy available at " a_RAND_DEV "\n", x.rpi.entropy_count); /* INT: entropy bits */ len = read(storfd, &x.rpi.entropy_count, sizeof x.rpi.entropy_count); if(len == -1){ fprintf(stderr, "Failed to read from %s: %s\n", store, strerror(errno)); rv = EX_IOERR; goto jerr2; } if(len != sizeof x.rpi.entropy_count){ fprintf(stderr, "Storage %s: seems corrupted (false format)\n", store); rv = EX_IOERR; goto jerr2; } if(x.rpi.entropy_count < 128 || x.rpi.entropy_count > a_RAND_NO_BYTES*8){ fprintf(stderr, "Storage %s seems corrupted (%d entropy bits)\n", store, x.rpi.entropy_count); rv = EX_IOERR; goto jerr2; } /* REST: pool bytes */ len = read(storfd, rpibuf, sizeof x.buf); if(len == -1){ fprintf(stderr, "Failed to read from %s: %s\n", store, strerror(errno)); rv = EX_IOERR; goto jerr2; } if(len == 0){ fprintf(stderr, "Storage %s: seems corrupted (no entropy)\n", store); rv = EX_TEMPFAIL; goto jerr2; } x.rpi.buf_size = (int)len; if(read(storfd, &accu, 1) != 0){ fprintf(stderr, "Storage %s: seems corrupted (no EOF seen)\n", store); rv = EX_IOERR; goto jerr2; } printf("- %d bytes / %d bits of entropy read from %s\n", x.rpi.buf_size, x.rpi.entropy_count, store); accu = ioctl(randfd, RNDADDENTROPY, &x.rpi); if(accu == -1){ fprintf(stderr, "Failed to add %d bits of entropy to " a_RAND_DEV ": %s\n", x.rpi.entropy_count, strerror(errno)); rv = EX_IOERR; goto jerr2; } printf("- Entropy added\n"); /* For at least statistics */ rv = ioctl(randfd, (int)RNDGETENTCNT, &iocarg); if(rv != -1) printf("- %d bits of entropy are at at " a_RAND_DEV "\n", iocarg); }else{ printf("- %d bits of entropy available at " a_RAND_DEV "%s\n", x.rpi.entropy_count, (x.rpi.entropy_count <= 128 ? ": temporary failure" : "")); if(x.rpi.entropy_count <= 128){ rv = EX_TEMPFAIL; goto jerr2; } len = read(randfd, rpibuf, sizeof x.buf); if(len == -1){ fprintf(stderr, "Failed to read from " a_RAND_DEV ": %s\n", strerror(errno)); rv = EX_IOERR; goto jerr2; } x.rpi.buf_size = (int)len; rv = ioctl(randfd, (int)RNDGETENTCNT, &iocarg); if(rv == -1){ fprintf(stderr, "Failed to query remaining entropy of " a_RAND_DEV ": %s\n", strerror(errno)); rv = EX_IOERR; goto jerr2; } printf("- %d bits of entropy remain at " a_RAND_DEV "\n", iocarg); x.rpi.entropy_count -= iocarg; if(x.rpi.entropy_count <= 128){ fprintf(stderr, "Insufficient entropy to save from " a_RAND_DEV " (%d bits)\n", x.rpi.entropy_count); rv = EX_TEMPFAIL; goto jerr2; } if((ssize_t)sizeof(x.rpi.entropy_count) != write(storfd, &x.rpi.entropy_count, sizeof x.rpi.entropy_count) || len != write(storfd, rpibuf, len)){ fprintf(stderr, "Failed to write to %s: %s\n", store, strerror(errno)); rv = EX_IOERR; goto jerr2; } printf("- %d bits / %d bytes of entropy saved to %s\n", x.rpi.entropy_count, x.rpi.buf_size, store); } rv = 0; jerr2: if(close(storfd) == -1) fprintf(stderr, "Error closing %s: %s\n", store, strerror(errno)); jerr1: if(close(randfd) == -1) fprintf(stderr, "Error closing " a_RAND_DEV ": %s\n", strerror(errno)); jleave: return rv; } /* s-it-mode */ --steffen | |Der Kragenbaer, The moon bear, |der holt sich munter he cheerfully and one by one |einen nach dem anderen runter wa.ks himself off |(By Robert Gernhardt) --- Unsubscribe: alpine-user+unsubscribe@lists.alpinelinux.org Help: alpine-user+help@lists.alpinelinux.org ---