if ( lu_breadcrumb_phys )
{
lu_stream_map(&lu_stream, lu_mfnlist_phys, lu_nr_pages);
+
+ lu_reserve_pages(&lu_stream);
}
if ( lu_bootmem_start )
--- /dev/null
+#include <xen/types.h>
+#include <xen/vmap.h>
+#include <xen/lu.h>
+#include <xen/sched.h>
+#include <xen/lu.h>
+
+#include <public/migration_stream.h>
+
+void lu_reserve_pages(struct lu_stream *stream)
+{
+ struct mr_rhdr *hdr;
+
+ while ( (hdr = lu_next_record(stream)) && hdr->type != REC_TYPE_END )
+ {
+ if ( hdr->type == REC_TYPE_LU_VERSION &&
+ hdr->length == sizeof(struct mr_lu_version) )
+ {
+ struct mr_lu_version *vers = LU_REC_DATA(hdr);
+
+ printk("Live update from Xen %d.%d\n",
+ vers->xen_major, vers->xen_minor);
+ }
+ }
+}
+
+/*
+ * Local variables:
+ * mode: C
+ * c-file-style: "BSD"
+ * c-basic-offset: 4
+ * tab-width: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
#include <xen/types.h>
#include <xen/mm.h>
+#include <public/migration_stream.h>
+
#define LIVE_UPDATE_MAGIC (0x4c69766555706461UL & PAGE_MASK)
struct lu_stream {
int lu_save_all(struct kexec_image *image);
void lu_stream_map(struct lu_stream *stream, unsigned long mfns_phys, int nr_pages);
+void lu_reserve_pages(struct lu_stream *stream);
+
+/* Pointer to the data immediately following a record header */
+#define LU_REC_DATA(hdr) ((void *)&(hdr)[1])
+
+static inline struct mr_rhdr *lu_next_record(struct lu_stream *stream)
+{
+ struct mr_rhdr *hdr = (struct mr_rhdr *)(stream->data + stream->last_hdr);
+
+ if (stream->len < stream->last_hdr + sizeof(*hdr) ||
+ stream->len < stream->last_hdr + sizeof(*hdr) + hdr->length)
+ return NULL;
+
+ stream->last_hdr += sizeof(*hdr) + ROUNDUP(hdr->length, 1<<REC_ALIGN_ORDER);
+ return hdr;
+}
#endif /* __XEN_LU_H__ */