+ if (bitmap_file) {
+ int uuid[4];
+
+ st->ss->uuid_from_super(uuid, super);
+ if (CreateBitmap(bitmap_file, force, (char*)uuid, bitmap_chunk,
+ delay, write_behind,
+ bitmapsize,
+ major)) {
+ return 1;
+ }
+ bitmap_fd = open(bitmap_file, O_RDWR);
+ if (bitmap_fd < 0) {
+ fprintf(stderr, Name ": weird: %s cannot be openned\n",
+ bitmap_file);
+ return 1;
+ }
+ if (ioctl(mdfd, SET_BITMAP_FILE, bitmap_fd) < 0) {
+ fprintf(stderr, Name ": Cannot set bitmap file for %s: %s\n",
+ mddev, strerror(errno));
+ return 1;
+ }
+ }
+
+
+
+ for (pass=1; pass <=2 ; pass++) {
+ mddev_dev_t moved_disk = NULL; /* the disk that was moved out of the insert point */
+
+ for (dnum=0, dv = devlist ; dv ;
+ dv=(dv->next)?(dv->next):moved_disk, dnum++) {
+ int fd;
+ struct stat stb;
+ mdu_disk_info_t disk;
+
+ disk.number = dnum;
+ if (dnum == insert_point) {
+ moved_disk = dv;
+ }
+ disk.raid_disk = disk.number;
+ if (disk.raid_disk < raiddisks)
+ disk.state = (1<<MD_DISK_ACTIVE) |
+ (1<<MD_DISK_SYNC);
+ else
+ disk.state = 0;
+ if (dv->writemostly)
+ disk.state |= (1<<MD_DISK_WRITEMOSTLY);
+
+ if (dnum == insert_point ||
+ strcasecmp(dv->devname, "missing")==0) {
+ disk.major = 0;
+ disk.minor = 0;
+ disk.state = (1<<MD_DISK_FAULTY);
+ } else {
+ fd = open(dv->devname, O_RDONLY|O_EXCL, 0);
+ if (fd < 0) {
+ fprintf(stderr, Name ": failed to open %s after earlier success - aborting\n",
+ dv->devname);
+ return 1;
+ }
+ fstat(fd, &stb);
+ disk.major = major(stb.st_rdev);
+ disk.minor = minor(stb.st_rdev);
+ close(fd);
+ }
+ switch(pass){
+ case 1:
+ st->ss->add_to_super(super, &disk);
+ break;
+ case 2:
+ if (disk.state == 1) break;
+ Kill(dv->devname, 0, 1); /* Just be sure it is clean */
+ Kill(dv->devname, 0, 1); /* and again, there could be two superblocks */
+ st->ss->write_init_super(st, super, &disk, dv->devname);
+
+ if (ioctl(mdfd, ADD_NEW_DISK, &disk)) {
+ fprintf(stderr, Name ": ADD_NEW_DISK for %s failed: %s\n",
+ dv->devname, strerror(errno));
+ free(super);
+ return 1;
+ }
+
+ break;
+ }
+ if (dv == moved_disk && dnum != insert_point) break;
+ }
+ }
+ free(super);
+