Compare commits
240 Commits
qemu-2.0.0
...
pull-sdl-2
Author | SHA1 | Date | |
---|---|---|---|
|
3f2fde2a00 | ||
|
8b15d9f1d2 | ||
|
e2da502c00 | ||
|
93156cef1c | ||
|
13de54eedd | ||
|
a41b2c995b | ||
|
d09a18d44d | ||
|
4a39cbb034 | ||
|
b87b8a8b32 | ||
|
7a30842186 | ||
|
b920cad669 | ||
|
00a9cacaea | ||
|
b0f9300ca3 | ||
|
9057698d93 | ||
|
d461863d3c | ||
|
7fb8b5d9c4 | ||
|
24c12b7923 | ||
|
6924bc1eef | ||
|
a629f2fdba | ||
|
5d77c8f9b6 | ||
|
a27b04577e | ||
|
296b14491a | ||
|
2d2ad6d090 | ||
|
6e1d3c1c85 | ||
|
e96e5ae880 | ||
|
eb6282f230 | ||
|
e3f9bb011a | ||
|
8439761852 | ||
|
172fc4dd33 | ||
|
f70edf9948 | ||
|
92de901290 | ||
|
4399c438a4 | ||
|
0fb6395c0c | ||
|
a28315ebaf | ||
|
460787605e | ||
|
9974ad40bf | ||
|
d1db760d7b | ||
|
1ba4b6a553 | ||
|
0b9f0e2fd7 | ||
|
1b7a0f758b | ||
|
c20499d985 | ||
|
c3481247e5 | ||
|
9083da1d4c | ||
|
638fb14169 | ||
|
2da1b3abbc | ||
|
bfa40f77af | ||
|
f7bdc41acc | ||
|
073a341151 | ||
|
0b15abfcbc | ||
|
f231b88db1 | ||
|
d73f0beadb | ||
|
4ad417baa4 | ||
|
4a66d3bf9a | ||
|
d876f60d14 | ||
|
027a79c373 | ||
|
02d1608980 | ||
|
411f491e0a | ||
|
f663faac3e | ||
|
b925965294 | ||
|
16cf0b2b34 | ||
|
13a12f869b | ||
|
7931b05987 | ||
|
44b0c0bbb5 | ||
|
860643bc5a | ||
|
9ffd26859d | ||
|
8c0124490b | ||
|
0e96643c98 | ||
|
ad600a4d49 | ||
|
ba3627ec38 | ||
|
4b8abfb78e | ||
|
370e681629 | ||
|
840a178c94 | ||
|
9b17031ac4 | ||
|
ac1307abfe | ||
|
409951f552 | ||
|
90d9d30152 | ||
|
f2d953ec31 | ||
|
9ffe333276 | ||
|
98522f63f4 | ||
|
5ff679b47d | ||
|
636ea3708c | ||
|
acd7fdc6d8 | ||
|
b8afb520e4 | ||
|
4ab9dab5b9 | ||
|
9ce10c0bdc | ||
|
da15ee5134 | ||
|
1dd3a44753 | ||
|
54db38a479 | ||
|
02eb19d0ec | ||
|
662deb908f | ||
|
f46fc4e6a9 | ||
|
df9ebea53e | ||
|
671c835b7d | ||
|
4b304cfae1 | ||
|
1194dcba22 | ||
|
170bf9315b | ||
|
f6c6afc1d4 | ||
|
d998e555d2 | ||
|
1976cccec8 | ||
|
50c5c4d125 | ||
|
20022fa15f | ||
|
ad5171dbd4 | ||
|
b36dc67b95 | ||
|
9d85d55732 | ||
|
2300aed15d | ||
|
e40cdb0e6e | ||
|
968fc24d84 | ||
|
423d00c857 | ||
|
ee25595f01 | ||
|
86e117724a | ||
|
d61ce900b9 | ||
|
1634df567d | ||
|
b321afbefd | ||
|
0374f5089a | ||
|
3bf16cb31a | ||
|
4bdd547aaa | ||
|
af9fe31070 | ||
|
1f91f39219 | ||
|
b672cf66c3 | ||
|
4c186ee2cf | ||
|
dcf91778ca | ||
|
2d03b49c3f | ||
|
e44a90c596 | ||
|
33bbd75a7c | ||
|
5538937368 | ||
|
6954a1cd97 | ||
|
15e3611e1c | ||
|
db302f8f93 | ||
|
6619bc5c55 | ||
|
103db49a10 | ||
|
286226a479 | ||
|
a63f9f85e3 | ||
|
323a8771cf | ||
|
2237094d96 | ||
|
1c70aa6264 | ||
|
f727d0e621 | ||
|
b5cde1da0a | ||
|
177311157c | ||
|
7633378d5f | ||
|
c29f9a0a29 | ||
|
f318cec6ad | ||
|
377a44ec8f | ||
|
3933443e38 | ||
|
19525524a7 | ||
|
f32cdad55d | ||
|
9449fdf61f | ||
|
00a29f3ddc | ||
|
85acfa9c38 | ||
|
1090b9c6cc | ||
|
2eef0bf821 | ||
|
014406b510 | ||
|
0ff644a786 | ||
|
cb1fa941c1 | ||
|
a50c0f5133 | ||
|
52e60cdd34 | ||
|
2f2a00aec9 | ||
|
a65f1de982 | ||
|
f502cfc207 | ||
|
a0618a1990 | ||
|
6cd8a2649a | ||
|
7e09797c29 | ||
|
aca3f40b37 | ||
|
9225d739e7 | ||
|
2c8dd31863 | ||
|
2c7ffc414d | ||
|
90e496386f | ||
|
8c6afa6ab1 | ||
|
00892383c9 | ||
|
d4a2dc675b | ||
|
8bcbf37caa | ||
|
abf1172fc6 | ||
|
c2b820fe58 | ||
|
ccd380876b | ||
|
c6138aabfb | ||
|
5149e557d7 | ||
|
06ef8604e9 | ||
|
39acc64741 | ||
|
e566be049a | ||
|
8f811b9a4a | ||
|
a9e05a1ceb | ||
|
0e154fe92c | ||
|
ef3765cb95 | ||
|
e8d8fef48f | ||
|
6580935246 | ||
|
76bff4f82f | ||
|
e20b8c04a3 | ||
|
8b0190bbde | ||
|
f477ed3c11 | ||
|
cd2754addc | ||
|
3d045dbca5 | ||
|
baee04abba | ||
|
b144be9e06 | ||
|
5e5863ecf1 | ||
|
9a734d64f9 | ||
|
9a8fa1bdad | ||
|
83ebb7cd01 | ||
|
42774a56ec | ||
|
958683482c | ||
|
cd2d46fd21 | ||
|
595b8fdd54 | ||
|
a4af30447b | ||
|
46010969f3 | ||
|
c67b67e511 | ||
|
1eaa1da7e4 | ||
|
8f56ced8aa | ||
|
89fe090bb3 | ||
|
6b88b37c0e | ||
|
075b8ddb9b | ||
|
de4d3555fa | ||
|
3bd67b7dab | ||
|
db4a16458c | ||
|
194cfb43d5 | ||
|
64f45e4991 | ||
|
5238c88657 | ||
|
67debe3ae5 | ||
|
b825025f08 | ||
|
a056c9faa4 | ||
|
3d4299f425 | ||
|
dc73dfd4bc | ||
|
edd8824cd4 | ||
|
e81864a109 | ||
|
de61d14fa7 | ||
|
667b1cdd4e | ||
|
9e4177ad6d | ||
|
dc0c8aaf2c | ||
|
ae7ab46aa8 | ||
|
6f4724672c | ||
|
38d195aa05 | ||
|
95f72aa90a | ||
|
d82b78e48b | ||
|
3d9e69a238 | ||
|
cae1f6f3e6 | ||
|
81d8a5ee19 | ||
|
c6e310d938 | ||
|
d8918df577 | ||
|
4ec4f0bd56 | ||
|
dfeb5fe770 | ||
|
929f8b5550 | ||
|
8bf56493f1 | ||
|
661f7fa4b0 |
18
.gitignore
vendored
18
.gitignore
vendored
@@ -18,8 +18,8 @@
|
||||
/*-darwin-user
|
||||
/*-linux-user
|
||||
/*-bsd-user
|
||||
libdis*
|
||||
libuser
|
||||
/libdis*
|
||||
/libuser
|
||||
/linux-headers/asm
|
||||
/qga/qapi-generated
|
||||
/qapi-generated
|
||||
@@ -49,19 +49,9 @@ libuser
|
||||
/qemu-monitor.texi
|
||||
/qmp-commands.txt
|
||||
/vscclient
|
||||
/test-bitops
|
||||
/test-coroutine
|
||||
/test-int128
|
||||
/test-opts-visitor
|
||||
/test-qmp-input-visitor
|
||||
/test-qmp-output-visitor
|
||||
/test-string-input-visitor
|
||||
/test-string-output-visitor
|
||||
/test-visitor-serialization
|
||||
/fsdev/virtfs-proxy-helper
|
||||
/fsdev/virtfs-proxy-helper.1
|
||||
/fsdev/virtfs-proxy-helper.pod
|
||||
/.gdbinit
|
||||
*.a
|
||||
*.aux
|
||||
*.cp
|
||||
@@ -90,12 +80,8 @@ libuser
|
||||
*.pc
|
||||
.libs
|
||||
.sdk
|
||||
*.swp
|
||||
*.orig
|
||||
.pc
|
||||
*.gcda
|
||||
*.gcno
|
||||
patches
|
||||
/pc-bios/bios-pq/status
|
||||
/pc-bios/vgabios-pq/status
|
||||
/pc-bios/optionrom/linuxboot.asm
|
||||
|
@@ -674,6 +674,8 @@ S: Supported
|
||||
F: block*
|
||||
F: block/
|
||||
F: hw/block/
|
||||
F: qemu-img*
|
||||
F: qemu-io*
|
||||
T: git git://repo.or.cz/qemu/kevin.git block
|
||||
T: git git://github.com/stefanha/qemu.git block
|
||||
|
||||
|
@@ -310,13 +310,28 @@ static int mig_save_device_bulk(QEMUFile *f, BlkMigDevState *bmds)
|
||||
|
||||
/* Called with iothread lock taken. */
|
||||
|
||||
static void set_dirty_tracking(void)
|
||||
static int set_dirty_tracking(void)
|
||||
{
|
||||
BlkMigDevState *bmds;
|
||||
int ret;
|
||||
|
||||
QSIMPLEQ_FOREACH(bmds, &block_mig_state.bmds_list, entry) {
|
||||
bmds->dirty_bitmap = bdrv_create_dirty_bitmap(bmds->bs, BLOCK_SIZE);
|
||||
bmds->dirty_bitmap = bdrv_create_dirty_bitmap(bmds->bs, BLOCK_SIZE,
|
||||
NULL);
|
||||
if (!bmds->dirty_bitmap) {
|
||||
ret = -errno;
|
||||
goto fail;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
|
||||
fail:
|
||||
QSIMPLEQ_FOREACH(bmds, &block_mig_state.bmds_list, entry) {
|
||||
if (bmds->dirty_bitmap) {
|
||||
bdrv_release_dirty_bitmap(bmds->bs, bmds->dirty_bitmap);
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void unset_dirty_tracking(void)
|
||||
@@ -611,10 +626,17 @@ static int block_save_setup(QEMUFile *f, void *opaque)
|
||||
block_mig_state.submitted, block_mig_state.transferred);
|
||||
|
||||
qemu_mutex_lock_iothread();
|
||||
init_blk_migration(f);
|
||||
|
||||
/* start track dirty blocks */
|
||||
set_dirty_tracking();
|
||||
ret = set_dirty_tracking();
|
||||
|
||||
if (ret) {
|
||||
qemu_mutex_unlock_iothread();
|
||||
return ret;
|
||||
}
|
||||
|
||||
init_blk_migration(f);
|
||||
|
||||
qemu_mutex_unlock_iothread();
|
||||
|
||||
ret = flush_blks(f);
|
||||
|
102
block.c
102
block.c
@@ -332,10 +332,21 @@ void bdrv_register(BlockDriver *bdrv)
|
||||
}
|
||||
|
||||
/* create a new block device (by default it is empty) */
|
||||
BlockDriverState *bdrv_new(const char *device_name)
|
||||
BlockDriverState *bdrv_new(const char *device_name, Error **errp)
|
||||
{
|
||||
BlockDriverState *bs;
|
||||
|
||||
if (bdrv_find(device_name)) {
|
||||
error_setg(errp, "Device with id '%s' already exists",
|
||||
device_name);
|
||||
return NULL;
|
||||
}
|
||||
if (bdrv_find_node(device_name)) {
|
||||
error_setg(errp, "Device with node-name '%s' already exists",
|
||||
device_name);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
bs = g_malloc0(sizeof(BlockDriverState));
|
||||
QLIST_INIT(&bs->dirty_bitmaps);
|
||||
pstrcpy(bs->device_name, sizeof(bs->device_name), device_name);
|
||||
@@ -788,38 +799,36 @@ static int bdrv_open_flags(BlockDriverState *bs, int flags)
|
||||
return open_flags;
|
||||
}
|
||||
|
||||
static int bdrv_assign_node_name(BlockDriverState *bs,
|
||||
const char *node_name,
|
||||
Error **errp)
|
||||
static void bdrv_assign_node_name(BlockDriverState *bs,
|
||||
const char *node_name,
|
||||
Error **errp)
|
||||
{
|
||||
if (!node_name) {
|
||||
return 0;
|
||||
return;
|
||||
}
|
||||
|
||||
/* empty string node name is invalid */
|
||||
if (node_name[0] == '\0') {
|
||||
error_setg(errp, "Empty node name");
|
||||
return -EINVAL;
|
||||
return;
|
||||
}
|
||||
|
||||
/* takes care of avoiding namespaces collisions */
|
||||
if (bdrv_find(node_name)) {
|
||||
error_setg(errp, "node-name=%s is conflicting with a device id",
|
||||
node_name);
|
||||
return -EINVAL;
|
||||
return;
|
||||
}
|
||||
|
||||
/* takes care of avoiding duplicates node names */
|
||||
if (bdrv_find_node(node_name)) {
|
||||
error_setg(errp, "Duplicate node name");
|
||||
return -EINVAL;
|
||||
return;
|
||||
}
|
||||
|
||||
/* copy node name into the bs and insert it into the graph list */
|
||||
pstrcpy(bs->node_name, sizeof(bs->node_name), node_name);
|
||||
QTAILQ_INSERT_TAIL(&graph_bdrv_states, bs, node_list);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -854,9 +863,10 @@ static int bdrv_open_common(BlockDriverState *bs, BlockDriverState *file,
|
||||
trace_bdrv_open_common(bs, filename ?: "", flags, drv->format_name);
|
||||
|
||||
node_name = qdict_get_try_str(options, "node-name");
|
||||
ret = bdrv_assign_node_name(bs, node_name, errp);
|
||||
if (ret < 0) {
|
||||
return ret;
|
||||
bdrv_assign_node_name(bs, node_name, &local_err);
|
||||
if (local_err) {
|
||||
error_propagate(errp, local_err);
|
||||
return -EINVAL;
|
||||
}
|
||||
qdict_del(options, "node-name");
|
||||
|
||||
@@ -1058,14 +1068,14 @@ fail:
|
||||
*/
|
||||
int bdrv_open_backing_file(BlockDriverState *bs, QDict *options, Error **errp)
|
||||
{
|
||||
char backing_filename[PATH_MAX];
|
||||
int back_flags, ret;
|
||||
char *backing_filename = g_malloc0(PATH_MAX);
|
||||
int back_flags, ret = 0;
|
||||
BlockDriver *back_drv = NULL;
|
||||
Error *local_err = NULL;
|
||||
|
||||
if (bs->backing_hd != NULL) {
|
||||
QDECREF(options);
|
||||
return 0;
|
||||
goto free_exit;
|
||||
}
|
||||
|
||||
/* NULL means an empty set of options */
|
||||
@@ -1078,10 +1088,9 @@ int bdrv_open_backing_file(BlockDriverState *bs, QDict *options, Error **errp)
|
||||
backing_filename[0] = '\0';
|
||||
} else if (bs->backing_file[0] == '\0' && qdict_size(options) == 0) {
|
||||
QDECREF(options);
|
||||
return 0;
|
||||
goto free_exit;
|
||||
} else {
|
||||
bdrv_get_full_backing_filename(bs, backing_filename,
|
||||
sizeof(backing_filename));
|
||||
bdrv_get_full_backing_filename(bs, backing_filename, PATH_MAX);
|
||||
}
|
||||
|
||||
if (bs->backing_format[0] != '\0') {
|
||||
@@ -1102,7 +1111,7 @@ int bdrv_open_backing_file(BlockDriverState *bs, QDict *options, Error **errp)
|
||||
error_setg(errp, "Could not open backing file: %s",
|
||||
error_get_pretty(local_err));
|
||||
error_free(local_err);
|
||||
return ret;
|
||||
goto free_exit;
|
||||
}
|
||||
|
||||
if (bs->backing_hd->file) {
|
||||
@@ -1113,7 +1122,9 @@ int bdrv_open_backing_file(BlockDriverState *bs, QDict *options, Error **errp)
|
||||
/* Recalculate the BlockLimits with the backing file */
|
||||
bdrv_refresh_limits(bs);
|
||||
|
||||
return 0;
|
||||
free_exit:
|
||||
g_free(backing_filename);
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -1170,8 +1181,7 @@ done:
|
||||
void bdrv_append_temp_snapshot(BlockDriverState *bs, Error **errp)
|
||||
{
|
||||
/* TODO: extra byte is a hack to ensure MAX_PATH space on Windows. */
|
||||
char tmp_filename[PATH_MAX + 1];
|
||||
|
||||
char *tmp_filename = g_malloc0(PATH_MAX + 1);
|
||||
int64_t total_size;
|
||||
BlockDriver *bdrv_qcow2;
|
||||
QEMUOptionParameter *create_options;
|
||||
@@ -1187,15 +1197,15 @@ void bdrv_append_temp_snapshot(BlockDriverState *bs, Error **errp)
|
||||
total_size = bdrv_getlength(bs);
|
||||
if (total_size < 0) {
|
||||
error_setg_errno(errp, -total_size, "Could not get image size");
|
||||
return;
|
||||
goto out;
|
||||
}
|
||||
total_size &= BDRV_SECTOR_MASK;
|
||||
|
||||
/* Create the temporary image */
|
||||
ret = get_tmp_filename(tmp_filename, sizeof(tmp_filename));
|
||||
ret = get_tmp_filename(tmp_filename, PATH_MAX + 1);
|
||||
if (ret < 0) {
|
||||
error_setg_errno(errp, -ret, "Could not get temporary filename");
|
||||
return;
|
||||
goto out;
|
||||
}
|
||||
|
||||
bdrv_qcow2 = bdrv_find_format("qcow2");
|
||||
@@ -1211,7 +1221,7 @@ void bdrv_append_temp_snapshot(BlockDriverState *bs, Error **errp)
|
||||
"'%s': %s", tmp_filename,
|
||||
error_get_pretty(local_err));
|
||||
error_free(local_err);
|
||||
return;
|
||||
goto out;
|
||||
}
|
||||
|
||||
/* Prepare a new options QDict for the temporary file */
|
||||
@@ -1221,17 +1231,20 @@ void bdrv_append_temp_snapshot(BlockDriverState *bs, Error **errp)
|
||||
qdict_put(snapshot_options, "file.filename",
|
||||
qstring_from_str(tmp_filename));
|
||||
|
||||
bs_snapshot = bdrv_new("");
|
||||
bs_snapshot = bdrv_new("", &error_abort);
|
||||
bs_snapshot->is_temporary = 1;
|
||||
|
||||
ret = bdrv_open(&bs_snapshot, NULL, NULL, snapshot_options,
|
||||
bs->open_flags & ~BDRV_O_SNAPSHOT, bdrv_qcow2, &local_err);
|
||||
if (ret < 0) {
|
||||
error_propagate(errp, local_err);
|
||||
return;
|
||||
goto out;
|
||||
}
|
||||
|
||||
bdrv_append(bs_snapshot, bs);
|
||||
|
||||
out:
|
||||
g_free(tmp_filename);
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -1288,7 +1301,7 @@ int bdrv_open(BlockDriverState **pbs, const char *filename,
|
||||
if (*pbs) {
|
||||
bs = *pbs;
|
||||
} else {
|
||||
bs = bdrv_new("");
|
||||
bs = bdrv_new("", &error_abort);
|
||||
}
|
||||
|
||||
/* NULL means an empty set of options */
|
||||
@@ -2581,6 +2594,10 @@ static int bdrv_check_byte_request(BlockDriverState *bs, int64_t offset,
|
||||
{
|
||||
int64_t len;
|
||||
|
||||
if (size > INT_MAX) {
|
||||
return -EIO;
|
||||
}
|
||||
|
||||
if (!bdrv_is_inserted(bs))
|
||||
return -ENOMEDIUM;
|
||||
|
||||
@@ -2601,7 +2618,7 @@ static int bdrv_check_byte_request(BlockDriverState *bs, int64_t offset,
|
||||
static int bdrv_check_request(BlockDriverState *bs, int64_t sector_num,
|
||||
int nb_sectors)
|
||||
{
|
||||
if (nb_sectors > INT_MAX / BDRV_SECTOR_SIZE) {
|
||||
if (nb_sectors < 0 || nb_sectors > INT_MAX / BDRV_SECTOR_SIZE) {
|
||||
return -EIO;
|
||||
}
|
||||
|
||||
@@ -2686,6 +2703,10 @@ static int bdrv_rw_co(BlockDriverState *bs, int64_t sector_num, uint8_t *buf,
|
||||
.iov_len = nb_sectors * BDRV_SECTOR_SIZE,
|
||||
};
|
||||
|
||||
if (nb_sectors < 0 || nb_sectors > INT_MAX / BDRV_SECTOR_SIZE) {
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
qemu_iovec_init_external(&qiov, &iov, 1);
|
||||
return bdrv_prwv_co(bs, sector_num << BDRV_SECTOR_BITS,
|
||||
&qiov, is_write, flags);
|
||||
@@ -2741,10 +2762,16 @@ int bdrv_write_zeroes(BlockDriverState *bs, int64_t sector_num,
|
||||
*/
|
||||
int bdrv_make_zero(BlockDriverState *bs, BdrvRequestFlags flags)
|
||||
{
|
||||
int64_t target_size = bdrv_getlength(bs) / BDRV_SECTOR_SIZE;
|
||||
int64_t target_size;
|
||||
int64_t ret, nb_sectors, sector_num = 0;
|
||||
int n;
|
||||
|
||||
target_size = bdrv_getlength(bs);
|
||||
if (target_size < 0) {
|
||||
return target_size;
|
||||
}
|
||||
target_size /= BDRV_SECTOR_SIZE;
|
||||
|
||||
for (;;) {
|
||||
nb_sectors = target_size - sector_num;
|
||||
if (nb_sectors <= 0) {
|
||||
@@ -5096,7 +5123,8 @@ bool bdrv_qiov_is_aligned(BlockDriverState *bs, QEMUIOVector *qiov)
|
||||
return true;
|
||||
}
|
||||
|
||||
BdrvDirtyBitmap *bdrv_create_dirty_bitmap(BlockDriverState *bs, int granularity)
|
||||
BdrvDirtyBitmap *bdrv_create_dirty_bitmap(BlockDriverState *bs, int granularity,
|
||||
Error **errp)
|
||||
{
|
||||
int64_t bitmap_size;
|
||||
BdrvDirtyBitmap *bitmap;
|
||||
@@ -5105,7 +5133,13 @@ BdrvDirtyBitmap *bdrv_create_dirty_bitmap(BlockDriverState *bs, int granularity)
|
||||
|
||||
granularity >>= BDRV_SECTOR_BITS;
|
||||
assert(granularity);
|
||||
bitmap_size = (bdrv_getlength(bs) >> BDRV_SECTOR_BITS);
|
||||
bitmap_size = bdrv_getlength(bs);
|
||||
if (bitmap_size < 0) {
|
||||
error_setg_errno(errp, -bitmap_size, "could not get length of device");
|
||||
errno = -bitmap_size;
|
||||
return NULL;
|
||||
}
|
||||
bitmap_size >>= BDRV_SECTOR_BITS;
|
||||
bitmap = g_malloc0(sizeof(BdrvDirtyBitmap));
|
||||
bitmap->bitmap = hbitmap_alloc(bitmap_size, ffs(granularity) - 1);
|
||||
QLIST_INSERT_HEAD(&bs->dirty_bitmaps, bitmap, list);
|
||||
|
@@ -72,7 +72,7 @@ static int cloop_open(BlockDriverState *bs, QDict *options, int flags,
|
||||
}
|
||||
s->block_size = be32_to_cpu(s->block_size);
|
||||
if (s->block_size % 512) {
|
||||
error_setg(errp, "block_size %u must be a multiple of 512",
|
||||
error_setg(errp, "block_size %" PRIu32 " must be a multiple of 512",
|
||||
s->block_size);
|
||||
return -EINVAL;
|
||||
}
|
||||
@@ -86,7 +86,7 @@ static int cloop_open(BlockDriverState *bs, QDict *options, int flags,
|
||||
* need a buffer this big.
|
||||
*/
|
||||
if (s->block_size > MAX_BLOCK_SIZE) {
|
||||
error_setg(errp, "block_size %u must be %u MB or less",
|
||||
error_setg(errp, "block_size %" PRIu32 " must be %u MB or less",
|
||||
s->block_size,
|
||||
MAX_BLOCK_SIZE / (1024 * 1024));
|
||||
return -EINVAL;
|
||||
@@ -101,7 +101,7 @@ static int cloop_open(BlockDriverState *bs, QDict *options, int flags,
|
||||
/* read offsets */
|
||||
if (s->n_blocks > (UINT32_MAX - 1) / sizeof(uint64_t)) {
|
||||
/* Prevent integer overflow */
|
||||
error_setg(errp, "n_blocks %u must be %zu or less",
|
||||
error_setg(errp, "n_blocks %" PRIu32 " must be %zu or less",
|
||||
s->n_blocks,
|
||||
(UINT32_MAX - 1) / sizeof(uint64_t));
|
||||
return -EINVAL;
|
||||
@@ -133,7 +133,7 @@ static int cloop_open(BlockDriverState *bs, QDict *options, int flags,
|
||||
|
||||
if (s->offsets[i] < s->offsets[i - 1]) {
|
||||
error_setg(errp, "offsets not monotonically increasing at "
|
||||
"index %u, image file is corrupt", i);
|
||||
"index %" PRIu32 ", image file is corrupt", i);
|
||||
ret = -EINVAL;
|
||||
goto fail;
|
||||
}
|
||||
@@ -146,8 +146,8 @@ static int cloop_open(BlockDriverState *bs, QDict *options, int flags,
|
||||
* ridiculous s->compressed_block allocation.
|
||||
*/
|
||||
if (size > 2 * MAX_BLOCK_SIZE) {
|
||||
error_setg(errp, "invalid compressed block size at index %u, "
|
||||
"image file is corrupt", i);
|
||||
error_setg(errp, "invalid compressed block size at index %" PRIu32
|
||||
", image file is corrupt", i);
|
||||
ret = -EINVAL;
|
||||
goto fail;
|
||||
}
|
||||
|
@@ -194,7 +194,7 @@ void commit_start(BlockDriverState *bs, BlockDriverState *base,
|
||||
if ((on_error == BLOCKDEV_ON_ERROR_STOP ||
|
||||
on_error == BLOCKDEV_ON_ERROR_ENOSPC) &&
|
||||
!bdrv_iostatus_is_enabled(bs)) {
|
||||
error_set(errp, QERR_INVALID_PARAMETER_COMBINATION);
|
||||
error_setg(errp, "Invalid parameter combination");
|
||||
return;
|
||||
}
|
||||
|
||||
|
@@ -543,7 +543,7 @@ static int curl_open(BlockDriverState *bs, QDict *options, int flags,
|
||||
return 0;
|
||||
|
||||
out:
|
||||
fprintf(stderr, "CURL: Error opening file: %s\n", state->errmsg);
|
||||
error_setg(errp, "CURL: Error opening file: %s", state->errmsg);
|
||||
curl_easy_cleanup(state->curl);
|
||||
state->curl = NULL;
|
||||
out_noclean:
|
||||
|
@@ -1095,16 +1095,15 @@ static struct scsi_task *iscsi_do_inquiry(struct iscsi_context *iscsi, int lun,
|
||||
*inq = scsi_datain_unmarshall(task);
|
||||
if (*inq == NULL) {
|
||||
error_setg(errp, "iSCSI: failed to unmarshall inquiry datain blob");
|
||||
goto fail;
|
||||
goto fail_with_err;
|
||||
}
|
||||
|
||||
return task;
|
||||
|
||||
fail:
|
||||
if (!error_is_set(errp)) {
|
||||
error_setg(errp, "iSCSI: Inquiry command failed : %s",
|
||||
iscsi_get_error(iscsi));
|
||||
}
|
||||
error_setg(errp, "iSCSI: Inquiry command failed : %s",
|
||||
iscsi_get_error(iscsi));
|
||||
fail_with_err:
|
||||
if (task != NULL) {
|
||||
scsi_free_scsi_task(task);
|
||||
}
|
||||
@@ -1401,7 +1400,7 @@ static int iscsi_create(const char *filename, QEMUOptionParameter *options,
|
||||
IscsiLun *iscsilun = NULL;
|
||||
QDict *bs_options;
|
||||
|
||||
bs = bdrv_new("");
|
||||
bs = bdrv_new("", &error_abort);
|
||||
|
||||
/* Read out options */
|
||||
while (options && options->name) {
|
||||
|
@@ -605,7 +605,10 @@ static void mirror_start_job(BlockDriverState *bs, BlockDriverState *target,
|
||||
s->granularity = granularity;
|
||||
s->buf_size = MAX(buf_size, granularity);
|
||||
|
||||
s->dirty_bitmap = bdrv_create_dirty_bitmap(bs, granularity);
|
||||
s->dirty_bitmap = bdrv_create_dirty_bitmap(bs, granularity, errp);
|
||||
if (!s->dirty_bitmap) {
|
||||
return;
|
||||
}
|
||||
bdrv_set_enable_write_cache(s->target, true);
|
||||
bdrv_set_on_error(s->target, on_target_error, on_target_error);
|
||||
bdrv_iostatus_enable(s->target);
|
||||
@@ -677,7 +680,7 @@ void commit_active_start(BlockDriverState *bs, BlockDriverState *base,
|
||||
mirror_start_job(bs, base, speed, 0, 0,
|
||||
on_error, on_error, cb, opaque, &local_err,
|
||||
&commit_active_job_driver, false, base);
|
||||
if (error_is_set(&local_err)) {
|
||||
if (local_err) {
|
||||
error_propagate(errp, local_err);
|
||||
goto error_restore_flags;
|
||||
}
|
||||
|
@@ -175,7 +175,7 @@ static void nbd_parse_filename(const char *filename, QDict *options,
|
||||
InetSocketAddress *addr = NULL;
|
||||
|
||||
addr = inet_parse(host_spec, errp);
|
||||
if (error_is_set(errp)) {
|
||||
if (!addr) {
|
||||
goto out;
|
||||
}
|
||||
|
||||
|
@@ -343,7 +343,7 @@ static int nfs_file_open(BlockDriverState *bs, QDict *options, int flags,
|
||||
|
||||
opts = qemu_opts_create(&runtime_opts, NULL, 0, &error_abort);
|
||||
qemu_opts_absorb_qdict(opts, options, &local_err);
|
||||
if (error_is_set(&local_err)) {
|
||||
if (local_err) {
|
||||
error_propagate(errp, local_err);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
16
block/qed.c
16
block/qed.c
@@ -650,19 +650,21 @@ static int bdrv_qed_create(const char *filename, QEMUOptionParameter *options,
|
||||
}
|
||||
|
||||
if (!qed_is_cluster_size_valid(cluster_size)) {
|
||||
fprintf(stderr, "QED cluster size must be within range [%u, %u] and power of 2\n",
|
||||
QED_MIN_CLUSTER_SIZE, QED_MAX_CLUSTER_SIZE);
|
||||
error_setg(errp, "QED cluster size must be within range [%u, %u] "
|
||||
"and power of 2",
|
||||
QED_MIN_CLUSTER_SIZE, QED_MAX_CLUSTER_SIZE);
|
||||
return -EINVAL;
|
||||
}
|
||||
if (!qed_is_table_size_valid(table_size)) {
|
||||
fprintf(stderr, "QED table size must be within range [%u, %u] and power of 2\n",
|
||||
QED_MIN_TABLE_SIZE, QED_MAX_TABLE_SIZE);
|
||||
error_setg(errp, "QED table size must be within range [%u, %u] "
|
||||
"and power of 2",
|
||||
QED_MIN_TABLE_SIZE, QED_MAX_TABLE_SIZE);
|
||||
return -EINVAL;
|
||||
}
|
||||
if (!qed_is_image_size_valid(image_size, cluster_size, table_size)) {
|
||||
fprintf(stderr, "QED image size must be a non-zero multiple of "
|
||||
"cluster size and less than %" PRIu64 " bytes\n",
|
||||
qed_max_image_size(cluster_size, table_size));
|
||||
error_setg(errp, "QED image size must be a non-zero multiple of "
|
||||
"cluster size and less than %" PRIu64 " bytes",
|
||||
qed_max_image_size(cluster_size, table_size));
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
|
@@ -753,7 +753,7 @@ static int quorum_open(BlockDriverState *bs, QDict *options, int flags,
|
||||
|
||||
opts = qemu_opts_create(&quorum_runtime_opts, NULL, 0, &error_abort);
|
||||
qemu_opts_absorb_qdict(opts, options, &local_err);
|
||||
if (error_is_set(&local_err)) {
|
||||
if (local_err) {
|
||||
ret = -EINVAL;
|
||||
goto exit;
|
||||
}
|
||||
@@ -828,7 +828,7 @@ close_exit:
|
||||
g_free(opened);
|
||||
exit:
|
||||
/* propagate error */
|
||||
if (error_is_set(&local_err)) {
|
||||
if (local_err) {
|
||||
error_propagate(errp, local_err);
|
||||
}
|
||||
QDECREF(list);
|
||||
|
23
block/vmdk.c
23
block/vmdk.c
@@ -262,7 +262,7 @@ static uint32_t vmdk_read_cid(BlockDriverState *bs, int parent)
|
||||
p_name = strstr(desc, cid_str);
|
||||
if (p_name != NULL) {
|
||||
p_name += cid_str_size;
|
||||
sscanf(p_name, "%x", &cid);
|
||||
sscanf(p_name, "%" SCNx32, &cid);
|
||||
}
|
||||
|
||||
return cid;
|
||||
@@ -290,7 +290,7 @@ static int vmdk_write_cid(BlockDriverState *bs, uint32_t cid)
|
||||
p_name = strstr(desc, "CID");
|
||||
if (p_name != NULL) {
|
||||
p_name += sizeof("CID");
|
||||
snprintf(p_name, sizeof(desc) - (p_name - desc), "%x\n", cid);
|
||||
snprintf(p_name, sizeof(desc) - (p_name - desc), "%" PRIx32 "\n", cid);
|
||||
pstrcat(desc, sizeof(desc), tmp_desc);
|
||||
}
|
||||
|
||||
@@ -640,7 +640,7 @@ static int vmdk_open_vmdk4(BlockDriverState *bs,
|
||||
|
||||
if (le32_to_cpu(header.version) > 3) {
|
||||
char buf[64];
|
||||
snprintf(buf, sizeof(buf), "VMDK version %d",
|
||||
snprintf(buf, sizeof(buf), "VMDK version %" PRId32,
|
||||
le32_to_cpu(header.version));
|
||||
error_set(errp, QERR_UNKNOWN_BLOCK_FORMAT_FEATURE,
|
||||
bs->device_name, "vmdk", buf);
|
||||
@@ -671,8 +671,9 @@ static int vmdk_open_vmdk4(BlockDriverState *bs,
|
||||
}
|
||||
if (bdrv_getlength(file) <
|
||||
le64_to_cpu(header.grain_offset) * BDRV_SECTOR_SIZE) {
|
||||
error_setg(errp, "File truncated, expecting at least %lld bytes",
|
||||
le64_to_cpu(header.grain_offset) * BDRV_SECTOR_SIZE);
|
||||
error_setg(errp, "File truncated, expecting at least %" PRId64 " bytes",
|
||||
(int64_t)(le64_to_cpu(header.grain_offset)
|
||||
* BDRV_SECTOR_SIZE));
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
@@ -1707,8 +1708,8 @@ static int vmdk_create(const char *filename, QEMUOptionParameter *options,
|
||||
const char desc_template[] =
|
||||
"# Disk DescriptorFile\n"
|
||||
"version=1\n"
|
||||
"CID=%x\n"
|
||||
"parentCID=%x\n"
|
||||
"CID=%" PRIx32 "\n"
|
||||
"parentCID=%" PRIx32 "\n"
|
||||
"createType=\"%s\"\n"
|
||||
"%s"
|
||||
"\n"
|
||||
@@ -1720,7 +1721,7 @@ static int vmdk_create(const char *filename, QEMUOptionParameter *options,
|
||||
"\n"
|
||||
"ddb.virtualHWVersion = \"%d\"\n"
|
||||
"ddb.geometry.cylinders = \"%" PRId64 "\"\n"
|
||||
"ddb.geometry.heads = \"%d\"\n"
|
||||
"ddb.geometry.heads = \"%" PRIu32 "\"\n"
|
||||
"ddb.geometry.sectors = \"63\"\n"
|
||||
"ddb.adapterType = \"%s\"\n";
|
||||
|
||||
@@ -1780,9 +1781,9 @@ static int vmdk_create(const char *filename, QEMUOptionParameter *options,
|
||||
strcmp(fmt, "twoGbMaxExtentFlat"));
|
||||
compress = !strcmp(fmt, "streamOptimized");
|
||||
if (flat) {
|
||||
desc_extent_line = "RW %lld FLAT \"%s\" 0\n";
|
||||
desc_extent_line = "RW %" PRId64 " FLAT \"%s\" 0\n";
|
||||
} else {
|
||||
desc_extent_line = "RW %lld SPARSE \"%s\"\n";
|
||||
desc_extent_line = "RW %" PRId64 " SPARSE \"%s\"\n";
|
||||
}
|
||||
if (flat && backing_file) {
|
||||
error_setg(errp, "Flat image can't have backing file");
|
||||
@@ -1850,7 +1851,7 @@ static int vmdk_create(const char *filename, QEMUOptionParameter *options,
|
||||
}
|
||||
/* generate descriptor file */
|
||||
desc = g_strdup_printf(desc_template,
|
||||
(unsigned int)time(NULL),
|
||||
(uint32_t)time(NULL),
|
||||
parent_cid,
|
||||
fmt,
|
||||
parent_desc_line,
|
||||
|
@@ -2947,7 +2947,7 @@ static int enable_write_target(BDRVVVFATState *s)
|
||||
unlink(s->qcow_filename);
|
||||
#endif
|
||||
|
||||
s->bs->backing_hd = bdrv_new("");
|
||||
s->bs->backing_hd = bdrv_new("", &error_abort);
|
||||
s->bs->backing_hd->drv = &vvfat_write_target;
|
||||
s->bs->backing_hd->opaque = g_malloc(sizeof(void*));
|
||||
*(void**)s->bs->backing_hd->opaque = s;
|
||||
|
31
blockdev.c
31
blockdev.c
@@ -452,16 +452,14 @@ static DriveInfo *blockdev_init(const char *file, QDict *bs_opts,
|
||||
}
|
||||
}
|
||||
|
||||
if (bdrv_find_node(qemu_opts_id(opts))) {
|
||||
error_setg(errp, "device id=%s is conflicting with a node-name",
|
||||
qemu_opts_id(opts));
|
||||
goto early_err;
|
||||
}
|
||||
|
||||
/* init */
|
||||
dinfo = g_malloc0(sizeof(*dinfo));
|
||||
dinfo->id = g_strdup(qemu_opts_id(opts));
|
||||
dinfo->bdrv = bdrv_new(dinfo->id);
|
||||
dinfo->bdrv = bdrv_new(dinfo->id, &error);
|
||||
if (error) {
|
||||
error_propagate(errp, error);
|
||||
goto bdrv_new_err;
|
||||
}
|
||||
dinfo->bdrv->open_flags = snapshot ? BDRV_O_SNAPSHOT : 0;
|
||||
dinfo->bdrv->read_only = ro;
|
||||
dinfo->refcount = 1;
|
||||
@@ -523,8 +521,9 @@ static DriveInfo *blockdev_init(const char *file, QDict *bs_opts,
|
||||
|
||||
err:
|
||||
bdrv_unref(dinfo->bdrv);
|
||||
g_free(dinfo->id);
|
||||
QTAILQ_REMOVE(&drives, dinfo, next);
|
||||
bdrv_new_err:
|
||||
g_free(dinfo->id);
|
||||
g_free(dinfo);
|
||||
early_err:
|
||||
QDECREF(bs_opts);
|
||||
@@ -1116,6 +1115,7 @@ typedef struct InternalSnapshotState {
|
||||
static void internal_snapshot_prepare(BlkTransactionState *common,
|
||||
Error **errp)
|
||||
{
|
||||
Error *local_err = NULL;
|
||||
const char *device;
|
||||
const char *name;
|
||||
BlockDriverState *bs;
|
||||
@@ -1164,8 +1164,10 @@ static void internal_snapshot_prepare(BlkTransactionState *common,
|
||||
}
|
||||
|
||||
/* check whether a snapshot with name exist */
|
||||
ret = bdrv_snapshot_find_by_id_and_name(bs, NULL, name, &old_sn, errp);
|
||||
if (error_is_set(errp)) {
|
||||
ret = bdrv_snapshot_find_by_id_and_name(bs, NULL, name, &old_sn,
|
||||
&local_err);
|
||||
if (local_err) {
|
||||
error_propagate(errp, local_err);
|
||||
return;
|
||||
} else if (ret) {
|
||||
error_setg(errp,
|
||||
@@ -1521,14 +1523,16 @@ static void eject_device(BlockDriverState *bs, int force, Error **errp)
|
||||
return;
|
||||
}
|
||||
if (!bdrv_dev_has_removable_media(bs)) {
|
||||
error_set(errp, QERR_DEVICE_NOT_REMOVABLE, bdrv_get_device_name(bs));
|
||||
error_setg(errp, "Device '%s' is not removable",
|
||||
bdrv_get_device_name(bs));
|
||||
return;
|
||||
}
|
||||
|
||||
if (bdrv_dev_is_medium_locked(bs) && !bdrv_dev_is_tray_open(bs)) {
|
||||
bdrv_dev_eject_request(bs, force);
|
||||
if (!force) {
|
||||
error_set(errp, QERR_DEVICE_LOCKED, bdrv_get_device_name(bs));
|
||||
error_setg(errp, "Device '%s' is locked",
|
||||
bdrv_get_device_name(bs));
|
||||
return;
|
||||
}
|
||||
}
|
||||
@@ -2220,7 +2224,8 @@ void qmp_block_job_cancel(const char *device,
|
||||
return;
|
||||
}
|
||||
if (job->paused && !force) {
|
||||
error_set(errp, QERR_BLOCK_JOB_PAUSED, device);
|
||||
error_setg(errp, "The block job for device '%s' is currently paused",
|
||||
device);
|
||||
return;
|
||||
}
|
||||
|
||||
|
@@ -88,7 +88,7 @@ void block_job_set_speed(BlockJob *job, int64_t speed, Error **errp)
|
||||
Error *local_err = NULL;
|
||||
|
||||
if (!job->driver->set_speed) {
|
||||
error_set(errp, QERR_NOT_SUPPORTED);
|
||||
error_set(errp, QERR_UNSUPPORTED);
|
||||
return;
|
||||
}
|
||||
job->driver->set_speed(job, speed, &local_err);
|
||||
|
12
configure
vendored
12
configure
vendored
@@ -1087,7 +1087,10 @@ for opt do
|
||||
;;
|
||||
--enable-quorum) quorum="yes"
|
||||
;;
|
||||
*) echo "ERROR: unknown option $opt"; show_help="yes"
|
||||
*)
|
||||
echo "ERROR: unknown option $opt"
|
||||
echo "Try '$0 --help' for more information"
|
||||
exit 1
|
||||
;;
|
||||
esac
|
||||
done
|
||||
@@ -1217,8 +1220,8 @@ Advanced options (experts only):
|
||||
--enable-modules enable modules support
|
||||
--enable-debug-tcg enable TCG debugging
|
||||
--disable-debug-tcg disable TCG debugging (default)
|
||||
--enable-debug-info enable debugging information (default)
|
||||
--disable-debug-info disable debugging information
|
||||
--enable-debug-info enable debugging information (default)
|
||||
--disable-debug-info disable debugging information
|
||||
--enable-debug enable common debug build options
|
||||
--enable-sparse enable sparse checker
|
||||
--disable-sparse disable sparse checker (default)
|
||||
@@ -1353,7 +1356,7 @@ Advanced options (experts only):
|
||||
|
||||
NOTE: The object files are built at the place where configure is launched
|
||||
EOF
|
||||
exit 1
|
||||
exit 0
|
||||
fi
|
||||
|
||||
# Now we have handled --enable-tcg-interpreter and know we're not just
|
||||
@@ -4095,7 +4098,6 @@ echo "sparse enabled $sparse"
|
||||
echo "strip binaries $strip_opt"
|
||||
echo "profiler $profiler"
|
||||
echo "static build $static"
|
||||
echo "-Werror enabled $werror"
|
||||
if test "$darwin" = "yes" ; then
|
||||
echo "Cocoa support $cocoa"
|
||||
fi
|
||||
|
2
cpus.c
2
cpus.c
@@ -1454,7 +1454,7 @@ void qmp_pmemsave(int64_t addr, int64_t size, const char *filename,
|
||||
l = sizeof(buf);
|
||||
if (l > size)
|
||||
l = size;
|
||||
cpu_physical_memory_rw(addr, buf, l, 0);
|
||||
cpu_physical_memory_read(addr, buf, l);
|
||||
if (fwrite(buf, 1, l, f) != l) {
|
||||
error_set(errp, QERR_IO_ERROR);
|
||||
goto exit;
|
||||
|
@@ -1,6 +1,7 @@
|
||||
CONFIG_USB_TABLET_WACOM=y
|
||||
CONFIG_USB_STORAGE_BOT=y
|
||||
CONFIG_USB_STORAGE_UAS=y
|
||||
CONFIG_USB_STORAGE_MTP=y
|
||||
CONFIG_USB_SMARTCARD=y
|
||||
CONFIG_USB_AUDIO=y
|
||||
CONFIG_USB_SERIAL=y
|
||||
|
@@ -311,7 +311,7 @@ void hmp_hello_world(Monitor *mon, const QDict *qdict)
|
||||
Error *errp = NULL;
|
||||
|
||||
qmp_hello_world(!!message, message, &errp);
|
||||
if (error_is_set(&errp)) {
|
||||
if (errp) {
|
||||
monitor_printf(mon, "%s\n", error_get_pretty(errp));
|
||||
error_free(errp);
|
||||
return;
|
||||
@@ -483,7 +483,7 @@ void hmp_info_alarm_clock(Monitor *mon)
|
||||
Error *errp = NULL;
|
||||
|
||||
clock = qmp_query_alarm_clock(&errp);
|
||||
if (error_is_set(&errp)) {
|
||||
if (errp) {
|
||||
monitor_printf(mon, "Could not query alarm clock information\n");
|
||||
error_free(errp);
|
||||
return;
|
||||
@@ -634,7 +634,7 @@ void hmp_info_alarm_methods(Monitor *mon)
|
||||
Error *errp = NULL;
|
||||
|
||||
method_list = qmp_query_alarm_methods(&errp);
|
||||
if (error_is_set(&errp)) {
|
||||
if (errp) {
|
||||
monitor_printf(mon, "Could not query alarm methods\n");
|
||||
error_free(errp);
|
||||
return;
|
||||
|
@@ -760,6 +760,7 @@ static int proxy_socket(const char *path, uid_t uid, gid_t gid)
|
||||
return -1;
|
||||
}
|
||||
|
||||
size = sizeof(qemu);
|
||||
client = accept(sock, (struct sockaddr *)&qemu, &size);
|
||||
if (client < 0) {
|
||||
do_perror("accept");
|
||||
|
@@ -176,7 +176,7 @@ ETEXI
|
||||
|
||||
{
|
||||
.name = "drive_del",
|
||||
.args_type = "id:s",
|
||||
.args_type = "id:B",
|
||||
.params = "device",
|
||||
.help = "remove host block device",
|
||||
.user_print = monitor_user_noop,
|
||||
@@ -658,6 +658,7 @@ ETEXI
|
||||
.help = "add device, like -device on the command line",
|
||||
.user_print = monitor_user_noop,
|
||||
.mhandler.cmd_new = do_device_add,
|
||||
.command_completion = device_add_completion,
|
||||
},
|
||||
|
||||
STEXI
|
||||
@@ -673,6 +674,7 @@ ETEXI
|
||||
.params = "device",
|
||||
.help = "remove device",
|
||||
.mhandler.cmd = hmp_device_del,
|
||||
.command_completion = device_del_completion,
|
||||
},
|
||||
|
||||
STEXI
|
||||
@@ -998,26 +1000,34 @@ ETEXI
|
||||
|
||||
{
|
||||
.name = "dump-guest-memory",
|
||||
.args_type = "paging:-p,filename:F,begin:i?,length:i?",
|
||||
.params = "[-p] filename [begin] [length]",
|
||||
.help = "dump guest memory to file"
|
||||
"\n\t\t\t begin(optional): the starting physical address"
|
||||
"\n\t\t\t length(optional): the memory size, in bytes",
|
||||
.args_type = "paging:-p,zlib:-z,lzo:-l,snappy:-s,filename:F,begin:i?,length:i?",
|
||||
.params = "[-p] [-z|-l|-s] filename [begin length]",
|
||||
.help = "dump guest memory into file 'filename'.\n\t\t\t"
|
||||
"-p: do paging to get guest's memory mapping.\n\t\t\t"
|
||||
"-z: dump in kdump-compressed format, with zlib compression.\n\t\t\t"
|
||||
"-l: dump in kdump-compressed format, with lzo compression.\n\t\t\t"
|
||||
"-s: dump in kdump-compressed format, with snappy compression.\n\t\t\t"
|
||||
"begin: the starting physical address.\n\t\t\t"
|
||||
"length: the memory size, in bytes.",
|
||||
.mhandler.cmd = hmp_dump_guest_memory,
|
||||
},
|
||||
|
||||
|
||||
STEXI
|
||||
@item dump-guest-memory [-p] @var{protocol} @var{begin} @var{length}
|
||||
@item dump-guest-memory [-p] @var{filename} @var{begin} @var{length}
|
||||
@item dump-guest-memory [-z|-l|-s] @var{filename}
|
||||
@findex dump-guest-memory
|
||||
Dump guest memory to @var{protocol}. The file can be processed with crash or
|
||||
gdb.
|
||||
filename: dump file name
|
||||
paging: do paging to get guest's memory mapping
|
||||
gdb. Without -z|-l|-s, the dump format is ELF.
|
||||
-p: do paging to get guest's memory mapping.
|
||||
-z: dump in kdump-compressed format, with zlib compression.
|
||||
-l: dump in kdump-compressed format, with lzo compression.
|
||||
-s: dump in kdump-compressed format, with snappy compression.
|
||||
filename: dump file name.
|
||||
begin: the starting physical address. It's optional, and should be
|
||||
specified with length together.
|
||||
specified together with length.
|
||||
length: the memory size, in bytes. It's optional, and should be specified
|
||||
with begin together.
|
||||
together with begin.
|
||||
ETEXI
|
||||
|
||||
{
|
||||
@@ -1254,6 +1264,7 @@ ETEXI
|
||||
.params = "[qom-type=]type,id=str[,prop=value][,...]",
|
||||
.help = "create QOM object",
|
||||
.mhandler.cmd = hmp_object_add,
|
||||
.command_completion = object_add_completion,
|
||||
},
|
||||
|
||||
STEXI
|
||||
@@ -1268,6 +1279,7 @@ ETEXI
|
||||
.params = "id",
|
||||
.help = "destroy QOM object",
|
||||
.mhandler.cmd = hmp_object_del,
|
||||
.command_completion = object_del_completion,
|
||||
},
|
||||
|
||||
STEXI
|
||||
|
25
hmp.c
25
hmp.c
@@ -1308,16 +1308,35 @@ void hmp_dump_guest_memory(Monitor *mon, const QDict *qdict)
|
||||
{
|
||||
Error *errp = NULL;
|
||||
int paging = qdict_get_try_bool(qdict, "paging", 0);
|
||||
int zlib = qdict_get_try_bool(qdict, "zlib", 0);
|
||||
int lzo = qdict_get_try_bool(qdict, "lzo", 0);
|
||||
int snappy = qdict_get_try_bool(qdict, "snappy", 0);
|
||||
const char *file = qdict_get_str(qdict, "filename");
|
||||
bool has_begin = qdict_haskey(qdict, "begin");
|
||||
bool has_length = qdict_haskey(qdict, "length");
|
||||
/* kdump-compressed format is not supported for HMP */
|
||||
bool has_format = false;
|
||||
int64_t begin = 0;
|
||||
int64_t length = 0;
|
||||
enum DumpGuestMemoryFormat dump_format = DUMP_GUEST_MEMORY_FORMAT_ELF;
|
||||
char *prot;
|
||||
|
||||
if (zlib + lzo + snappy > 1) {
|
||||
error_setg(&errp, "only one of '-z|-l|-s' can be set");
|
||||
hmp_handle_error(mon, &errp);
|
||||
return;
|
||||
}
|
||||
|
||||
if (zlib) {
|
||||
dump_format = DUMP_GUEST_MEMORY_FORMAT_KDUMP_ZLIB;
|
||||
}
|
||||
|
||||
if (lzo) {
|
||||
dump_format = DUMP_GUEST_MEMORY_FORMAT_KDUMP_LZO;
|
||||
}
|
||||
|
||||
if (snappy) {
|
||||
dump_format = DUMP_GUEST_MEMORY_FORMAT_KDUMP_SNAPPY;
|
||||
}
|
||||
|
||||
if (has_begin) {
|
||||
begin = qdict_get_int(qdict, "begin");
|
||||
}
|
||||
@@ -1328,7 +1347,7 @@ void hmp_dump_guest_memory(Monitor *mon, const QDict *qdict)
|
||||
prot = g_strconcat("file:", file, NULL);
|
||||
|
||||
qmp_dump_guest_memory(paging, prot, has_begin, begin, has_length, length,
|
||||
has_format, dump_format, &errp);
|
||||
true, dump_format, &errp);
|
||||
hmp_handle_error(mon, &errp);
|
||||
g_free(prot);
|
||||
}
|
||||
|
5
hmp.h
5
hmp.h
@@ -15,6 +15,7 @@
|
||||
#define HMP_H
|
||||
|
||||
#include "qemu-common.h"
|
||||
#include "qemu/readline.h"
|
||||
#include "qapi-types.h"
|
||||
#include "qapi/qmp/qdict.h"
|
||||
|
||||
@@ -92,5 +93,9 @@ void hmp_qemu_io(Monitor *mon, const QDict *qdict);
|
||||
void hmp_cpu_add(Monitor *mon, const QDict *qdict);
|
||||
void hmp_object_add(Monitor *mon, const QDict *qdict);
|
||||
void hmp_object_del(Monitor *mon, const QDict *qdict);
|
||||
void object_add_completion(ReadLineState *rs, int nb_args, const char *str);
|
||||
void object_del_completion(ReadLineState *rs, int nb_args, const char *str);
|
||||
void device_add_completion(ReadLineState *rs, int nb_args, const char *str);
|
||||
void device_del_completion(ReadLineState *rs, int nb_args, const char *str);
|
||||
|
||||
#endif
|
||||
|
@@ -987,8 +987,9 @@ static void v9fs_attach(void *opaque)
|
||||
*/
|
||||
if (!s->migration_blocker) {
|
||||
s->root_fid = fid;
|
||||
error_set(&s->migration_blocker, QERR_VIRTFS_FEATURE_BLOCKS_MIGRATION,
|
||||
s->ctx.fs_root ? s->ctx.fs_root : "NULL", s->tag);
|
||||
error_setg(&s->migration_blocker,
|
||||
"Migration is disabled when VirtFS export path '%s' is mounted in the guest using mount_tag '%s'",
|
||||
s->ctx.fs_root ? s->ctx.fs_root : "NULL", s->tag);
|
||||
migrate_add_blocker(s->migration_blocker);
|
||||
}
|
||||
out:
|
||||
|
@@ -43,6 +43,19 @@ static void cubieboard_init(QEMUMachineInitArgs *args)
|
||||
exit(1);
|
||||
}
|
||||
|
||||
object_property_set_int(OBJECT(&s->a10->timer), 32768, "clk0-freq", &err);
|
||||
if (err != NULL) {
|
||||
error_report("Couldn't set clk0 frequency: %s", error_get_pretty(err));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
object_property_set_int(OBJECT(&s->a10->timer), 24000000, "clk1-freq",
|
||||
&err);
|
||||
if (err != NULL) {
|
||||
error_report("Couldn't set clk1 frequency: %s", error_get_pretty(err));
|
||||
exit(1);
|
||||
}
|
||||
|
||||
object_property_set_bool(OBJECT(s->a10), true, "realized", &err);
|
||||
if (err != NULL) {
|
||||
error_report("Couldn't realize Allwinner A10: %s",
|
||||
|
@@ -817,11 +817,14 @@ static int blk_connect(struct XenDevice *xendev)
|
||||
index = (blkdev->xendev.dev - 202 * 256) / 16;
|
||||
blkdev->dinfo = drive_get(IF_XEN, 0, index);
|
||||
if (!blkdev->dinfo) {
|
||||
Error *local_err = NULL;
|
||||
/* setup via xenbus -> create new block driver instance */
|
||||
xen_be_printf(&blkdev->xendev, 2, "create new bdrv (xenbus setup)\n");
|
||||
blkdev->bs = bdrv_new(blkdev->dev);
|
||||
blkdev->bs = bdrv_new(blkdev->dev, &local_err);
|
||||
if (local_err) {
|
||||
blkdev->bs = NULL;
|
||||
}
|
||||
if (blkdev->bs) {
|
||||
Error *local_err = NULL;
|
||||
BlockDriver *drv = bdrv_find_whitelisted_format(blkdev->fileproto,
|
||||
readonly);
|
||||
if (bdrv_open(&blkdev->bs, blkdev->filename, NULL, NULL, qflags,
|
||||
|
@@ -587,8 +587,9 @@ static void set_blocksize(Object *obj, Visitor *v, void *opaque,
|
||||
|
||||
/* We rely on power-of-2 blocksizes for bitmasks */
|
||||
if ((value & (value - 1)) != 0) {
|
||||
error_set(errp, QERR_PROPERTY_VALUE_NOT_POWER_OF_2,
|
||||
dev->id?:"", name, (int64_t)value);
|
||||
error_setg(errp,
|
||||
"Property %s.%s doesn't take value '%" PRId64 "', it's not a power of 2",
|
||||
dev->id ?: "", name, (int64_t)value);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -853,7 +854,7 @@ void error_set_from_qdev_prop_error(Error **errp, int ret, DeviceState *dev,
|
||||
{
|
||||
switch (ret) {
|
||||
case -EEXIST:
|
||||
error_set(errp, QERR_PROPERTY_VALUE_IN_USE,
|
||||
error_setg(errp, "Property '%s.%s' can't take value '%s', it's in use",
|
||||
object_get_typename(OBJECT(dev)), prop->name, value);
|
||||
break;
|
||||
default:
|
||||
@@ -862,7 +863,7 @@ void error_set_from_qdev_prop_error(Error **errp, int ret, DeviceState *dev,
|
||||
object_get_typename(OBJECT(dev)), prop->name, value);
|
||||
break;
|
||||
case -ENOENT:
|
||||
error_set(errp, QERR_PROPERTY_VALUE_NOT_FOUND,
|
||||
error_setg(errp, "Property '%s.%s' can't find value '%s'",
|
||||
object_get_typename(OBJECT(dev)), prop->name, value);
|
||||
break;
|
||||
case 0:
|
||||
|
@@ -71,7 +71,7 @@ static void eeprom_write_data(SMBusDevice *dev, uint8_t cmd, uint8_t *buf, int l
|
||||
printf("eeprom_write_byte: addr=0x%02x cmd=0x%02x val=0x%02x\n",
|
||||
dev->i2c.address, cmd, buf[0]);
|
||||
#endif
|
||||
/* An page write operation is not a valid SMBus command.
|
||||
/* A page write operation is not a valid SMBus command.
|
||||
It is a block write without a length byte. Fortunately we
|
||||
get the full block anyway. */
|
||||
/* TODO: Should this set the current location? */
|
||||
|
@@ -124,14 +124,14 @@ static const TPRInstruction tpr_instr[] = {
|
||||
|
||||
static void read_guest_rom_state(VAPICROMState *s)
|
||||
{
|
||||
cpu_physical_memory_rw(s->rom_state_paddr, (void *)&s->rom_state,
|
||||
sizeof(GuestROMState), 0);
|
||||
cpu_physical_memory_read(s->rom_state_paddr, &s->rom_state,
|
||||
sizeof(GuestROMState));
|
||||
}
|
||||
|
||||
static void write_guest_rom_state(VAPICROMState *s)
|
||||
{
|
||||
cpu_physical_memory_rw(s->rom_state_paddr, (void *)&s->rom_state,
|
||||
sizeof(GuestROMState), 1);
|
||||
cpu_physical_memory_write(s->rom_state_paddr, &s->rom_state,
|
||||
sizeof(GuestROMState));
|
||||
}
|
||||
|
||||
static void update_guest_rom_state(VAPICROMState *s)
|
||||
@@ -311,16 +311,14 @@ static int update_rom_mapping(VAPICROMState *s, CPUX86State *env, target_ulong i
|
||||
for (pos = le32_to_cpu(s->rom_state.fixup_start);
|
||||
pos < le32_to_cpu(s->rom_state.fixup_end);
|
||||
pos += 4) {
|
||||
cpu_physical_memory_rw(paddr + pos - s->rom_state.vaddr,
|
||||
(void *)&offset, sizeof(offset), 0);
|
||||
cpu_physical_memory_read(paddr + pos - s->rom_state.vaddr,
|
||||
&offset, sizeof(offset));
|
||||
offset = le32_to_cpu(offset);
|
||||
cpu_physical_memory_rw(paddr + offset, (void *)&patch,
|
||||
sizeof(patch), 0);
|
||||
cpu_physical_memory_read(paddr + offset, &patch, sizeof(patch));
|
||||
patch = le32_to_cpu(patch);
|
||||
patch += rom_state_vaddr - le32_to_cpu(s->rom_state.vaddr);
|
||||
patch = cpu_to_le32(patch);
|
||||
cpu_physical_memory_rw(paddr + offset, (void *)&patch,
|
||||
sizeof(patch), 1);
|
||||
cpu_physical_memory_write(paddr + offset, &patch, sizeof(patch));
|
||||
}
|
||||
read_guest_rom_state(s);
|
||||
s->vapic_paddr = paddr + le32_to_cpu(s->rom_state.vapic_vaddr) -
|
||||
@@ -364,8 +362,8 @@ static int vapic_enable(VAPICROMState *s, X86CPU *cpu)
|
||||
}
|
||||
vapic_paddr = s->vapic_paddr +
|
||||
(((hwaddr)cpu_number) << VAPIC_CPU_SHIFT);
|
||||
cpu_physical_memory_rw(vapic_paddr + offsetof(VAPICState, enabled),
|
||||
(void *)&enabled, sizeof(enabled), 1);
|
||||
cpu_physical_memory_write(vapic_paddr + offsetof(VAPICState, enabled),
|
||||
&enabled, sizeof(enabled));
|
||||
apic_enable_vapic(cpu->apic_state, vapic_paddr);
|
||||
|
||||
s->state = VAPIC_ACTIVE;
|
||||
@@ -535,7 +533,7 @@ static int patch_hypercalls(VAPICROMState *s)
|
||||
uint8_t *rom;
|
||||
|
||||
rom = g_malloc(s->rom_size);
|
||||
cpu_physical_memory_rw(rom_paddr, rom, s->rom_size, 0);
|
||||
cpu_physical_memory_read(rom_paddr, rom, s->rom_size);
|
||||
|
||||
for (pos = 0; pos < s->rom_size - sizeof(vmcall_pattern); pos++) {
|
||||
if (kvm_irqchip_in_kernel()) {
|
||||
@@ -551,8 +549,7 @@ static int patch_hypercalls(VAPICROMState *s)
|
||||
}
|
||||
if (memcmp(rom + pos, pattern, 7) == 0 &&
|
||||
(rom[pos + 7] == alternates[0] || rom[pos + 7] == alternates[1])) {
|
||||
cpu_physical_memory_rw(rom_paddr + pos + 5, (uint8_t *)patch,
|
||||
3, 1);
|
||||
cpu_physical_memory_write(rom_paddr + pos + 5, patch, 3);
|
||||
/*
|
||||
* Don't flush the tb here. Under ordinary conditions, the patched
|
||||
* calls are miles away from the current IP. Under malicious
|
||||
@@ -760,8 +757,8 @@ static int vapic_post_load(void *opaque, int version_id)
|
||||
run_on_cpu(first_cpu, do_vapic_enable, s);
|
||||
} else {
|
||||
zero = g_malloc0(s->rom_state.vapic_size);
|
||||
cpu_physical_memory_rw(s->vapic_paddr, zero,
|
||||
s->rom_state.vapic_size, 1);
|
||||
cpu_physical_memory_write(s->vapic_paddr, zero,
|
||||
s->rom_state.vapic_size);
|
||||
g_free(zero);
|
||||
}
|
||||
}
|
||||
|
@@ -438,9 +438,9 @@ static void check_cmd(AHCIState *s, int port)
|
||||
|
||||
if ((pr->cmd & PORT_CMD_START) && pr->cmd_issue) {
|
||||
for (slot = 0; (slot < 32) && pr->cmd_issue; slot++) {
|
||||
if ((pr->cmd_issue & (1 << slot)) &&
|
||||
if ((pr->cmd_issue & (1U << slot)) &&
|
||||
!handle_cmd(s, port, slot)) {
|
||||
pr->cmd_issue &= ~(1 << slot);
|
||||
pr->cmd_issue &= ~(1U << slot);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -23,11 +23,20 @@
|
||||
static void aw_a10_pic_update(AwA10PICState *s)
|
||||
{
|
||||
uint8_t i;
|
||||
int irq = 0, fiq = 0;
|
||||
int irq = 0, fiq = 0, pending;
|
||||
|
||||
s->vector = 0;
|
||||
|
||||
for (i = 0; i < AW_A10_PIC_REG_NUM; i++) {
|
||||
irq |= s->irq_pending[i] & ~s->mask[i];
|
||||
fiq |= s->select[i] & s->irq_pending[i] & ~s->mask[i];
|
||||
|
||||
if (!s->vector) {
|
||||
pending = ffs(s->irq_pending[i] & ~s->mask[i]);
|
||||
if (pending) {
|
||||
s->vector = (i * 32 + pending - 1) * 4;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
qemu_set_irq(s->parent_irq, !!irq);
|
||||
@@ -40,6 +49,8 @@ static void aw_a10_pic_set_irq(void *opaque, int irq, int level)
|
||||
|
||||
if (level) {
|
||||
set_bit(irq % 32, (void *)&s->irq_pending[irq / 32]);
|
||||
} else {
|
||||
clear_bit(irq % 32, (void *)&s->irq_pending[irq / 32]);
|
||||
}
|
||||
aw_a10_pic_update(s);
|
||||
}
|
||||
@@ -84,9 +95,6 @@ static void aw_a10_pic_write(void *opaque, hwaddr offset, uint64_t value,
|
||||
uint8_t index = (offset & 0xc) / 4;
|
||||
|
||||
switch (offset) {
|
||||
case AW_A10_PIC_VECTOR:
|
||||
s->vector = value & ~0x3;
|
||||
break;
|
||||
case AW_A10_PIC_BASE_ADDR:
|
||||
s->base_addr = value & ~0x3;
|
||||
case AW_A10_PIC_PROTECT:
|
||||
@@ -96,7 +104,11 @@ static void aw_a10_pic_write(void *opaque, hwaddr offset, uint64_t value,
|
||||
s->nmi = value;
|
||||
break;
|
||||
case AW_A10_PIC_IRQ_PENDING ... AW_A10_PIC_IRQ_PENDING + 8:
|
||||
s->irq_pending[index] &= ~value;
|
||||
/*
|
||||
* The register is read-only; nevertheless, Linux (including
|
||||
* the version originally shipped by Allwinner) pretends to
|
||||
* write to the register. Just ignore it.
|
||||
*/
|
||||
break;
|
||||
case AW_A10_PIC_FIQ_PENDING ... AW_A10_PIC_FIQ_PENDING + 8:
|
||||
s->fiq_pending[index] &= ~value;
|
||||
|
@@ -98,8 +98,8 @@ static void apic_sync_vapic(APICCommonState *s, int sync_type)
|
||||
return;
|
||||
}
|
||||
if (sync_type & SYNC_FROM_VAPIC) {
|
||||
cpu_physical_memory_rw(s->vapic_paddr, (void *)&vapic_state,
|
||||
sizeof(vapic_state), 0);
|
||||
cpu_physical_memory_read(s->vapic_paddr, &vapic_state,
|
||||
sizeof(vapic_state));
|
||||
s->tpr = vapic_state.tpr;
|
||||
}
|
||||
if (sync_type & (SYNC_TO_VAPIC | SYNC_ISR_IRR_TO_VAPIC)) {
|
||||
|
@@ -684,8 +684,8 @@ static int pci_ivshmem_init(PCIDevice *dev)
|
||||
}
|
||||
|
||||
if (s->role_val == IVSHMEM_PEER) {
|
||||
error_set(&s->migration_blocker, QERR_DEVICE_FEATURE_BLOCKS_MIGRATION,
|
||||
"peer mode", "ivshmem");
|
||||
error_setg(&s->migration_blocker,
|
||||
"Migration is disabled when using feature 'peer mode' in device 'ivshmem'");
|
||||
migrate_add_blocker(s->migration_blocker);
|
||||
}
|
||||
|
||||
|
@@ -19,102 +19,155 @@
|
||||
#include "hw/sysbus.h"
|
||||
#include "sysemu/sysemu.h"
|
||||
|
||||
#ifdef ZYNQ_ARM_SLCR_ERR_DEBUG
|
||||
#define DB_PRINT(...) do { \
|
||||
fprintf(stderr, ": %s: ", __func__); \
|
||||
fprintf(stderr, ## __VA_ARGS__); \
|
||||
} while (0);
|
||||
#else
|
||||
#define DB_PRINT(...)
|
||||
#ifndef ZYNQ_SLCR_ERR_DEBUG
|
||||
#define ZYNQ_SLCR_ERR_DEBUG 0
|
||||
#endif
|
||||
|
||||
#define DB_PRINT(...) do { \
|
||||
if (ZYNQ_SLCR_ERR_DEBUG) { \
|
||||
fprintf(stderr, ": %s: ", __func__); \
|
||||
fprintf(stderr, ## __VA_ARGS__); \
|
||||
} \
|
||||
} while (0);
|
||||
|
||||
#define XILINX_LOCK_KEY 0x767b
|
||||
#define XILINX_UNLOCK_KEY 0xdf0d
|
||||
|
||||
#define R_PSS_RST_CTRL_SOFT_RST 0x1
|
||||
|
||||
typedef enum {
|
||||
ARM_PLL_CTRL,
|
||||
DDR_PLL_CTRL,
|
||||
IO_PLL_CTRL,
|
||||
PLL_STATUS,
|
||||
ARM_PPL_CFG,
|
||||
DDR_PLL_CFG,
|
||||
IO_PLL_CFG,
|
||||
PLL_BG_CTRL,
|
||||
PLL_MAX
|
||||
} PLLValues;
|
||||
enum {
|
||||
SCL = 0x000 / 4,
|
||||
LOCK,
|
||||
UNLOCK,
|
||||
LOCKSTA,
|
||||
|
||||
typedef enum {
|
||||
ARM_CLK_CTRL,
|
||||
DDR_CLK_CTRL,
|
||||
DCI_CLK_CTRL,
|
||||
APER_CLK_CTRL,
|
||||
USB0_CLK_CTRL,
|
||||
USB1_CLK_CTRL,
|
||||
GEM0_RCLK_CTRL,
|
||||
GEM1_RCLK_CTRL,
|
||||
GEM0_CLK_CTRL,
|
||||
GEM1_CLK_CTRL,
|
||||
SMC_CLK_CTRL,
|
||||
LQSPI_CLK_CTRL,
|
||||
SDIO_CLK_CTRL,
|
||||
UART_CLK_CTRL,
|
||||
SPI_CLK_CTRL,
|
||||
CAN_CLK_CTRL,
|
||||
CAN_MIOCLK_CTRL,
|
||||
DBG_CLK_CTRL,
|
||||
PCAP_CLK_CTRL,
|
||||
TOPSW_CLK_CTRL,
|
||||
CLK_MAX
|
||||
} ClkValues;
|
||||
ARM_PLL_CTRL = 0x100 / 4,
|
||||
DDR_PLL_CTRL,
|
||||
IO_PLL_CTRL,
|
||||
PLL_STATUS,
|
||||
ARM_PLL_CFG,
|
||||
DDR_PLL_CFG,
|
||||
IO_PLL_CFG,
|
||||
|
||||
typedef enum {
|
||||
CLK_CTRL,
|
||||
THR_CTRL,
|
||||
THR_CNT,
|
||||
THR_STA,
|
||||
FPGA_MAX
|
||||
} FPGAValues;
|
||||
ARM_CLK_CTRL = 0x120 / 4,
|
||||
DDR_CLK_CTRL,
|
||||
DCI_CLK_CTRL,
|
||||
APER_CLK_CTRL,
|
||||
USB0_CLK_CTRL,
|
||||
USB1_CLK_CTRL,
|
||||
GEM0_RCLK_CTRL,
|
||||
GEM1_RCLK_CTRL,
|
||||
GEM0_CLK_CTRL,
|
||||
GEM1_CLK_CTRL,
|
||||
SMC_CLK_CTRL,
|
||||
LQSPI_CLK_CTRL,
|
||||
SDIO_CLK_CTRL,
|
||||
UART_CLK_CTRL,
|
||||
SPI_CLK_CTRL,
|
||||
CAN_CLK_CTRL,
|
||||
CAN_MIOCLK_CTRL,
|
||||
DBG_CLK_CTRL,
|
||||
PCAP_CLK_CTRL,
|
||||
TOPSW_CLK_CTRL,
|
||||
|
||||
typedef enum {
|
||||
SYNC_CTRL,
|
||||
SYNC_STATUS,
|
||||
BANDGAP_TRIP,
|
||||
CC_TEST,
|
||||
PLL_PREDIVISOR,
|
||||
CLK_621_TRUE,
|
||||
PICTURE_DBG,
|
||||
PICTURE_DBG_UCNT,
|
||||
PICTURE_DBG_LCNT,
|
||||
MISC_MAX
|
||||
} MiscValues;
|
||||
#define FPGA_CTRL_REGS(n, start) \
|
||||
FPGA ## n ## _CLK_CTRL = (start) / 4, \
|
||||
FPGA ## n ## _THR_CTRL, \
|
||||
FPGA ## n ## _THR_CNT, \
|
||||
FPGA ## n ## _THR_STA,
|
||||
FPGA_CTRL_REGS(0, 0x170)
|
||||
FPGA_CTRL_REGS(1, 0x180)
|
||||
FPGA_CTRL_REGS(2, 0x190)
|
||||
FPGA_CTRL_REGS(3, 0x1a0)
|
||||
|
||||
typedef enum {
|
||||
PSS,
|
||||
DDDR,
|
||||
DMAC = 3,
|
||||
USB,
|
||||
GEM,
|
||||
SDIO,
|
||||
SPI,
|
||||
CAN,
|
||||
I2C,
|
||||
UART,
|
||||
GPIO,
|
||||
LQSPI,
|
||||
SMC,
|
||||
OCM,
|
||||
DEVCI,
|
||||
FPGA,
|
||||
A9_CPU,
|
||||
RS_AWDT,
|
||||
RST_REASON,
|
||||
RST_REASON_CLR,
|
||||
REBOOT_STATUS,
|
||||
BOOT_MODE,
|
||||
RESET_MAX
|
||||
} ResetValues;
|
||||
BANDGAP_TRIP = 0x1b8 / 4,
|
||||
PLL_PREDIVISOR = 0x1c0 / 4,
|
||||
CLK_621_TRUE,
|
||||
|
||||
PSS_RST_CTRL = 0x200 / 4,
|
||||
DDR_RST_CTRL,
|
||||
TOPSW_RESET_CTRL,
|
||||
DMAC_RST_CTRL,
|
||||
USB_RST_CTRL,
|
||||
GEM_RST_CTRL,
|
||||
SDIO_RST_CTRL,
|
||||
SPI_RST_CTRL,
|
||||
CAN_RST_CTRL,
|
||||
I2C_RST_CTRL,
|
||||
UART_RST_CTRL,
|
||||
GPIO_RST_CTRL,
|
||||
LQSPI_RST_CTRL,
|
||||
SMC_RST_CTRL,
|
||||
OCM_RST_CTRL,
|
||||
FPGA_RST_CTRL = 0x240 / 4,
|
||||
A9_CPU_RST_CTRL,
|
||||
|
||||
RS_AWDT_CTRL = 0x24c / 4,
|
||||
RST_REASON,
|
||||
|
||||
REBOOT_STATUS = 0x258 / 4,
|
||||
BOOT_MODE,
|
||||
|
||||
APU_CTRL = 0x300 / 4,
|
||||
WDT_CLK_SEL,
|
||||
|
||||
TZ_DMA_NS = 0x440 / 4,
|
||||
TZ_DMA_IRQ_NS,
|
||||
TZ_DMA_PERIPH_NS,
|
||||
|
||||
PSS_IDCODE = 0x530 / 4,
|
||||
|
||||
DDR_URGENT = 0x600 / 4,
|
||||
DDR_CAL_START = 0x60c / 4,
|
||||
DDR_REF_START = 0x614 / 4,
|
||||
DDR_CMD_STA,
|
||||
DDR_URGENT_SEL,
|
||||
DDR_DFI_STATUS,
|
||||
|
||||
MIO = 0x700 / 4,
|
||||
#define MIO_LENGTH 54
|
||||
|
||||
MIO_LOOPBACK = 0x804 / 4,
|
||||
MIO_MST_TRI0,
|
||||
MIO_MST_TRI1,
|
||||
|
||||
SD0_WP_CD_SEL = 0x830 / 4,
|
||||
SD1_WP_CD_SEL,
|
||||
|
||||
LVL_SHFTR_EN = 0x900 / 4,
|
||||
OCM_CFG = 0x910 / 4,
|
||||
|
||||
CPU_RAM = 0xa00 / 4,
|
||||
|
||||
IOU = 0xa30 / 4,
|
||||
|
||||
DMAC_RAM = 0xa50 / 4,
|
||||
|
||||
AFI0 = 0xa60 / 4,
|
||||
AFI1 = AFI0 + 3,
|
||||
AFI2 = AFI1 + 3,
|
||||
AFI3 = AFI2 + 3,
|
||||
#define AFI_LENGTH 3
|
||||
|
||||
OCM = 0xa90 / 4,
|
||||
|
||||
DEVCI_RAM = 0xaa0 / 4,
|
||||
|
||||
CSG_RAM = 0xab0 / 4,
|
||||
|
||||
GPIOB_CTRL = 0xb00 / 4,
|
||||
GPIOB_CFG_CMOS18,
|
||||
GPIOB_CFG_CMOS25,
|
||||
GPIOB_CFG_CMOS33,
|
||||
GPIOB_CFG_HSTL = 0xb14 / 4,
|
||||
GPIOB_DRVR_BIAS_CTRL,
|
||||
|
||||
DDRIOB = 0xb40 / 4,
|
||||
#define DDRIOB_LENGTH 14
|
||||
};
|
||||
|
||||
#define ZYNQ_SLCR_MMIO_SIZE 0x1000
|
||||
#define ZYNQ_SLCR_NUM_REGS (ZYNQ_SLCR_MMIO_SIZE / 4)
|
||||
|
||||
#define TYPE_ZYNQ_SLCR "xilinx,zynq_slcr"
|
||||
#define ZYNQ_SLCR(obj) OBJECT_CHECK(ZynqSLCRState, (obj), TYPE_ZYNQ_SLCR)
|
||||
@@ -124,42 +177,7 @@ typedef struct ZynqSLCRState {
|
||||
|
||||
MemoryRegion iomem;
|
||||
|
||||
union {
|
||||
struct {
|
||||
uint16_t scl;
|
||||
uint16_t lockval;
|
||||
uint32_t pll[PLL_MAX]; /* 0x100 - 0x11C */
|
||||
uint32_t clk[CLK_MAX]; /* 0x120 - 0x16C */
|
||||
uint32_t fpga[4][FPGA_MAX]; /* 0x170 - 0x1AC */
|
||||
uint32_t misc[MISC_MAX]; /* 0x1B0 - 0x1D8 */
|
||||
uint32_t reset[RESET_MAX]; /* 0x200 - 0x25C */
|
||||
uint32_t apu_ctrl; /* 0x300 */
|
||||
uint32_t wdt_clk_sel; /* 0x304 */
|
||||
uint32_t tz_ocm[3]; /* 0x400 - 0x408 */
|
||||
uint32_t tz_ddr; /* 0x430 */
|
||||
uint32_t tz_dma[3]; /* 0x440 - 0x448 */
|
||||
uint32_t tz_misc[3]; /* 0x450 - 0x458 */
|
||||
uint32_t tz_fpga[2]; /* 0x484 - 0x488 */
|
||||
uint32_t dbg_ctrl; /* 0x500 */
|
||||
uint32_t pss_idcode; /* 0x530 */
|
||||
uint32_t ddr[8]; /* 0x600 - 0x620 - 0x604-missing */
|
||||
uint32_t mio[54]; /* 0x700 - 0x7D4 */
|
||||
uint32_t mio_func[4]; /* 0x800 - 0x810 */
|
||||
uint32_t sd[2]; /* 0x830 - 0x834 */
|
||||
uint32_t lvl_shftr_en; /* 0x900 */
|
||||
uint32_t ocm_cfg; /* 0x910 */
|
||||
uint32_t cpu_ram[8]; /* 0xA00 - 0xA1C */
|
||||
uint32_t iou[7]; /* 0xA30 - 0xA48 */
|
||||
uint32_t dmac_ram; /* 0xA50 */
|
||||
uint32_t afi[4][3]; /* 0xA60 - 0xA8C */
|
||||
uint32_t ocm[3]; /* 0xA90 - 0xA98 */
|
||||
uint32_t devci_ram; /* 0xAA0 */
|
||||
uint32_t csg_ram; /* 0xAB0 */
|
||||
uint32_t gpiob[12]; /* 0xB00 - 0xB2C */
|
||||
uint32_t ddriob[14]; /* 0xB40 - 0xB74 */
|
||||
};
|
||||
uint8_t data[0x1000];
|
||||
};
|
||||
uint32_t regs[ZYNQ_SLCR_NUM_REGS];
|
||||
} ZynqSLCRState;
|
||||
|
||||
static void zynq_slcr_reset(DeviceState *d)
|
||||
@@ -169,177 +187,169 @@ static void zynq_slcr_reset(DeviceState *d)
|
||||
|
||||
DB_PRINT("RESET\n");
|
||||
|
||||
s->lockval = 1;
|
||||
s->regs[LOCKSTA] = 1;
|
||||
/* 0x100 - 0x11C */
|
||||
s->pll[ARM_PLL_CTRL] = 0x0001A008;
|
||||
s->pll[DDR_PLL_CTRL] = 0x0001A008;
|
||||
s->pll[IO_PLL_CTRL] = 0x0001A008;
|
||||
s->pll[PLL_STATUS] = 0x0000003F;
|
||||
s->pll[ARM_PPL_CFG] = 0x00014000;
|
||||
s->pll[DDR_PLL_CFG] = 0x00014000;
|
||||
s->pll[IO_PLL_CFG] = 0x00014000;
|
||||
s->regs[ARM_PLL_CTRL] = 0x0001A008;
|
||||
s->regs[DDR_PLL_CTRL] = 0x0001A008;
|
||||
s->regs[IO_PLL_CTRL] = 0x0001A008;
|
||||
s->regs[PLL_STATUS] = 0x0000003F;
|
||||
s->regs[ARM_PLL_CFG] = 0x00014000;
|
||||
s->regs[DDR_PLL_CFG] = 0x00014000;
|
||||
s->regs[IO_PLL_CFG] = 0x00014000;
|
||||
|
||||
/* 0x120 - 0x16C */
|
||||
s->clk[ARM_CLK_CTRL] = 0x1F000400;
|
||||
s->clk[DDR_CLK_CTRL] = 0x18400003;
|
||||
s->clk[DCI_CLK_CTRL] = 0x01E03201;
|
||||
s->clk[APER_CLK_CTRL] = 0x01FFCCCD;
|
||||
s->clk[USB0_CLK_CTRL] = s->clk[USB1_CLK_CTRL] = 0x00101941;
|
||||
s->clk[GEM0_RCLK_CTRL] = s->clk[GEM1_RCLK_CTRL] = 0x00000001;
|
||||
s->clk[GEM0_CLK_CTRL] = s->clk[GEM1_CLK_CTRL] = 0x00003C01;
|
||||
s->clk[SMC_CLK_CTRL] = 0x00003C01;
|
||||
s->clk[LQSPI_CLK_CTRL] = 0x00002821;
|
||||
s->clk[SDIO_CLK_CTRL] = 0x00001E03;
|
||||
s->clk[UART_CLK_CTRL] = 0x00003F03;
|
||||
s->clk[SPI_CLK_CTRL] = 0x00003F03;
|
||||
s->clk[CAN_CLK_CTRL] = 0x00501903;
|
||||
s->clk[DBG_CLK_CTRL] = 0x00000F03;
|
||||
s->clk[PCAP_CLK_CTRL] = 0x00000F01;
|
||||
s->regs[ARM_CLK_CTRL] = 0x1F000400;
|
||||
s->regs[DDR_CLK_CTRL] = 0x18400003;
|
||||
s->regs[DCI_CLK_CTRL] = 0x01E03201;
|
||||
s->regs[APER_CLK_CTRL] = 0x01FFCCCD;
|
||||
s->regs[USB0_CLK_CTRL] = s->regs[USB1_CLK_CTRL] = 0x00101941;
|
||||
s->regs[GEM0_RCLK_CTRL] = s->regs[GEM1_RCLK_CTRL] = 0x00000001;
|
||||
s->regs[GEM0_CLK_CTRL] = s->regs[GEM1_CLK_CTRL] = 0x00003C01;
|
||||
s->regs[SMC_CLK_CTRL] = 0x00003C01;
|
||||
s->regs[LQSPI_CLK_CTRL] = 0x00002821;
|
||||
s->regs[SDIO_CLK_CTRL] = 0x00001E03;
|
||||
s->regs[UART_CLK_CTRL] = 0x00003F03;
|
||||
s->regs[SPI_CLK_CTRL] = 0x00003F03;
|
||||
s->regs[CAN_CLK_CTRL] = 0x00501903;
|
||||
s->regs[DBG_CLK_CTRL] = 0x00000F03;
|
||||
s->regs[PCAP_CLK_CTRL] = 0x00000F01;
|
||||
|
||||
/* 0x170 - 0x1AC */
|
||||
s->fpga[0][CLK_CTRL] = s->fpga[1][CLK_CTRL] = s->fpga[2][CLK_CTRL] =
|
||||
s->fpga[3][CLK_CTRL] = 0x00101800;
|
||||
s->fpga[0][THR_STA] = s->fpga[1][THR_STA] = s->fpga[2][THR_STA] =
|
||||
s->fpga[3][THR_STA] = 0x00010000;
|
||||
s->regs[FPGA0_CLK_CTRL] = s->regs[FPGA1_CLK_CTRL] = s->regs[FPGA2_CLK_CTRL]
|
||||
= s->regs[FPGA3_CLK_CTRL] = 0x00101800;
|
||||
s->regs[FPGA0_THR_STA] = s->regs[FPGA1_THR_STA] = s->regs[FPGA2_THR_STA]
|
||||
= s->regs[FPGA3_THR_STA] = 0x00010000;
|
||||
|
||||
/* 0x1B0 - 0x1D8 */
|
||||
s->misc[BANDGAP_TRIP] = 0x0000001F;
|
||||
s->misc[PLL_PREDIVISOR] = 0x00000001;
|
||||
s->misc[CLK_621_TRUE] = 0x00000001;
|
||||
s->regs[BANDGAP_TRIP] = 0x0000001F;
|
||||
s->regs[PLL_PREDIVISOR] = 0x00000001;
|
||||
s->regs[CLK_621_TRUE] = 0x00000001;
|
||||
|
||||
/* 0x200 - 0x25C */
|
||||
s->reset[FPGA] = 0x01F33F0F;
|
||||
s->reset[RST_REASON] = 0x00000040;
|
||||
s->regs[FPGA_RST_CTRL] = 0x01F33F0F;
|
||||
s->regs[RST_REASON] = 0x00000040;
|
||||
|
||||
s->regs[BOOT_MODE] = 0x00000001;
|
||||
|
||||
/* 0x700 - 0x7D4 */
|
||||
for (i = 0; i < 54; i++) {
|
||||
s->mio[i] = 0x00001601;
|
||||
s->regs[MIO + i] = 0x00001601;
|
||||
}
|
||||
for (i = 2; i <= 8; i++) {
|
||||
s->mio[i] = 0x00000601;
|
||||
s->regs[MIO + i] = 0x00000601;
|
||||
}
|
||||
|
||||
/* MIO_MST_TRI0, MIO_MST_TRI1 */
|
||||
s->mio_func[2] = s->mio_func[3] = 0xFFFFFFFF;
|
||||
s->regs[MIO_MST_TRI0] = s->regs[MIO_MST_TRI1] = 0xFFFFFFFF;
|
||||
|
||||
s->cpu_ram[0] = s->cpu_ram[1] = s->cpu_ram[3] =
|
||||
s->cpu_ram[4] = s->cpu_ram[7] = 0x00010101;
|
||||
s->cpu_ram[2] = s->cpu_ram[5] = 0x01010101;
|
||||
s->cpu_ram[6] = 0x00000001;
|
||||
s->regs[CPU_RAM + 0] = s->regs[CPU_RAM + 1] = s->regs[CPU_RAM + 3]
|
||||
= s->regs[CPU_RAM + 4] = s->regs[CPU_RAM + 7]
|
||||
= 0x00010101;
|
||||
s->regs[CPU_RAM + 2] = s->regs[CPU_RAM + 5] = 0x01010101;
|
||||
s->regs[CPU_RAM + 6] = 0x00000001;
|
||||
|
||||
s->iou[0] = s->iou[1] = s->iou[2] = s->iou[3] = 0x09090909;
|
||||
s->iou[4] = s->iou[5] = 0x00090909;
|
||||
s->iou[6] = 0x00000909;
|
||||
s->regs[IOU + 0] = s->regs[IOU + 1] = s->regs[IOU + 2] = s->regs[IOU + 3]
|
||||
= 0x09090909;
|
||||
s->regs[IOU + 4] = s->regs[IOU + 5] = 0x00090909;
|
||||
s->regs[IOU + 6] = 0x00000909;
|
||||
|
||||
s->dmac_ram = 0x00000009;
|
||||
s->regs[DMAC_RAM] = 0x00000009;
|
||||
|
||||
s->afi[0][0] = s->afi[0][1] = 0x09090909;
|
||||
s->afi[1][0] = s->afi[1][1] = 0x09090909;
|
||||
s->afi[2][0] = s->afi[2][1] = 0x09090909;
|
||||
s->afi[3][0] = s->afi[3][1] = 0x09090909;
|
||||
s->afi[0][2] = s->afi[1][2] = s->afi[2][2] = s->afi[3][2] = 0x00000909;
|
||||
s->regs[AFI0 + 0] = s->regs[AFI0 + 1] = 0x09090909;
|
||||
s->regs[AFI1 + 0] = s->regs[AFI1 + 1] = 0x09090909;
|
||||
s->regs[AFI2 + 0] = s->regs[AFI2 + 1] = 0x09090909;
|
||||
s->regs[AFI3 + 0] = s->regs[AFI3 + 1] = 0x09090909;
|
||||
s->regs[AFI0 + 2] = s->regs[AFI1 + 2] = s->regs[AFI2 + 2]
|
||||
= s->regs[AFI3 + 2] = 0x00000909;
|
||||
|
||||
s->ocm[0] = 0x01010101;
|
||||
s->ocm[1] = s->ocm[2] = 0x09090909;
|
||||
s->regs[OCM + 0] = 0x01010101;
|
||||
s->regs[OCM + 1] = s->regs[OCM + 2] = 0x09090909;
|
||||
|
||||
s->devci_ram = 0x00000909;
|
||||
s->csg_ram = 0x00000001;
|
||||
s->regs[DEVCI_RAM] = 0x00000909;
|
||||
s->regs[CSG_RAM] = 0x00000001;
|
||||
|
||||
s->ddriob[0] = s->ddriob[1] = s->ddriob[2] = s->ddriob[3] = 0x00000e00;
|
||||
s->ddriob[4] = s->ddriob[5] = s->ddriob[6] = 0x00000e00;
|
||||
s->ddriob[12] = 0x00000021;
|
||||
s->regs[DDRIOB + 0] = s->regs[DDRIOB + 1] = s->regs[DDRIOB + 2]
|
||||
= s->regs[DDRIOB + 3] = 0x00000e00;
|
||||
s->regs[DDRIOB + 4] = s->regs[DDRIOB + 5] = s->regs[DDRIOB + 6]
|
||||
= 0x00000e00;
|
||||
s->regs[DDRIOB + 12] = 0x00000021;
|
||||
}
|
||||
|
||||
static inline uint32_t zynq_slcr_read_imp(void *opaque,
|
||||
hwaddr offset)
|
||||
{
|
||||
ZynqSLCRState *s = (ZynqSLCRState *)opaque;
|
||||
|
||||
static bool zynq_slcr_check_offset(hwaddr offset, bool rnw)
|
||||
{
|
||||
switch (offset) {
|
||||
case 0x0: /* SCL */
|
||||
return s->scl;
|
||||
case 0x4: /* LOCK */
|
||||
case 0x8: /* UNLOCK */
|
||||
DB_PRINT("Reading SCLR_LOCK/UNLOCK is not enabled\n");
|
||||
return 0;
|
||||
case 0x0C: /* LOCKSTA */
|
||||
return s->lockval;
|
||||
case 0x100 ... 0x11C:
|
||||
return s->pll[(offset - 0x100) / 4];
|
||||
case 0x120 ... 0x16C:
|
||||
return s->clk[(offset - 0x120) / 4];
|
||||
case 0x170 ... 0x1AC:
|
||||
return s->fpga[0][(offset - 0x170) / 4];
|
||||
case 0x1B0 ... 0x1D8:
|
||||
return s->misc[(offset - 0x1B0) / 4];
|
||||
case 0x200 ... 0x258:
|
||||
return s->reset[(offset - 0x200) / 4];
|
||||
case 0x25c:
|
||||
return 1;
|
||||
case 0x300:
|
||||
return s->apu_ctrl;
|
||||
case 0x304:
|
||||
return s->wdt_clk_sel;
|
||||
case 0x400 ... 0x408:
|
||||
return s->tz_ocm[(offset - 0x400) / 4];
|
||||
case 0x430:
|
||||
return s->tz_ddr;
|
||||
case 0x440 ... 0x448:
|
||||
return s->tz_dma[(offset - 0x440) / 4];
|
||||
case 0x450 ... 0x458:
|
||||
return s->tz_misc[(offset - 0x450) / 4];
|
||||
case 0x484 ... 0x488:
|
||||
return s->tz_fpga[(offset - 0x484) / 4];
|
||||
case 0x500:
|
||||
return s->dbg_ctrl;
|
||||
case 0x530:
|
||||
return s->pss_idcode;
|
||||
case 0x600 ... 0x620:
|
||||
if (offset == 0x604) {
|
||||
goto bad_reg;
|
||||
}
|
||||
return s->ddr[(offset - 0x600) / 4];
|
||||
case 0x700 ... 0x7D4:
|
||||
return s->mio[(offset - 0x700) / 4];
|
||||
case 0x800 ... 0x810:
|
||||
return s->mio_func[(offset - 0x800) / 4];
|
||||
case 0x830 ... 0x834:
|
||||
return s->sd[(offset - 0x830) / 4];
|
||||
case 0x900:
|
||||
return s->lvl_shftr_en;
|
||||
case 0x910:
|
||||
return s->ocm_cfg;
|
||||
case 0xA00 ... 0xA1C:
|
||||
return s->cpu_ram[(offset - 0xA00) / 4];
|
||||
case 0xA30 ... 0xA48:
|
||||
return s->iou[(offset - 0xA30) / 4];
|
||||
case 0xA50:
|
||||
return s->dmac_ram;
|
||||
case 0xA60 ... 0xA8C:
|
||||
return s->afi[0][(offset - 0xA60) / 4];
|
||||
case 0xA90 ... 0xA98:
|
||||
return s->ocm[(offset - 0xA90) / 4];
|
||||
case 0xAA0:
|
||||
return s->devci_ram;
|
||||
case 0xAB0:
|
||||
return s->csg_ram;
|
||||
case 0xB00 ... 0xB2C:
|
||||
return s->gpiob[(offset - 0xB00) / 4];
|
||||
case 0xB40 ... 0xB74:
|
||||
return s->ddriob[(offset - 0xB40) / 4];
|
||||
case LOCK:
|
||||
case UNLOCK:
|
||||
case DDR_CAL_START:
|
||||
case DDR_REF_START:
|
||||
return !rnw; /* Write only */
|
||||
case LOCKSTA:
|
||||
case FPGA0_THR_STA:
|
||||
case FPGA1_THR_STA:
|
||||
case FPGA2_THR_STA:
|
||||
case FPGA3_THR_STA:
|
||||
case BOOT_MODE:
|
||||
case PSS_IDCODE:
|
||||
case DDR_CMD_STA:
|
||||
case DDR_DFI_STATUS:
|
||||
case PLL_STATUS:
|
||||
return rnw;/* read only */
|
||||
case SCL:
|
||||
case ARM_PLL_CTRL ... IO_PLL_CTRL:
|
||||
case ARM_PLL_CFG ... IO_PLL_CFG:
|
||||
case ARM_CLK_CTRL ... TOPSW_CLK_CTRL:
|
||||
case FPGA0_CLK_CTRL ... FPGA0_THR_CNT:
|
||||
case FPGA1_CLK_CTRL ... FPGA1_THR_CNT:
|
||||
case FPGA2_CLK_CTRL ... FPGA2_THR_CNT:
|
||||
case FPGA3_CLK_CTRL ... FPGA3_THR_CNT:
|
||||
case BANDGAP_TRIP:
|
||||
case PLL_PREDIVISOR:
|
||||
case CLK_621_TRUE:
|
||||
case PSS_RST_CTRL ... A9_CPU_RST_CTRL:
|
||||
case RS_AWDT_CTRL:
|
||||
case RST_REASON:
|
||||
case REBOOT_STATUS:
|
||||
case APU_CTRL:
|
||||
case WDT_CLK_SEL:
|
||||
case TZ_DMA_NS ... TZ_DMA_PERIPH_NS:
|
||||
case DDR_URGENT:
|
||||
case DDR_URGENT_SEL:
|
||||
case MIO ... MIO + MIO_LENGTH - 1:
|
||||
case MIO_LOOPBACK ... MIO_MST_TRI1:
|
||||
case SD0_WP_CD_SEL:
|
||||
case SD1_WP_CD_SEL:
|
||||
case LVL_SHFTR_EN:
|
||||
case OCM_CFG:
|
||||
case CPU_RAM:
|
||||
case IOU:
|
||||
case DMAC_RAM:
|
||||
case AFI0 ... AFI3 + AFI_LENGTH - 1:
|
||||
case OCM:
|
||||
case DEVCI_RAM:
|
||||
case CSG_RAM:
|
||||
case GPIOB_CTRL ... GPIOB_CFG_CMOS33:
|
||||
case GPIOB_CFG_HSTL:
|
||||
case GPIOB_DRVR_BIAS_CTRL:
|
||||
case DDRIOB ... DDRIOB + DDRIOB_LENGTH - 1:
|
||||
return true;
|
||||
default:
|
||||
bad_reg:
|
||||
DB_PRINT("Bad register offset 0x%x\n", (int)offset);
|
||||
return 0;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
static uint64_t zynq_slcr_read(void *opaque, hwaddr offset,
|
||||
unsigned size)
|
||||
{
|
||||
uint32_t ret = zynq_slcr_read_imp(opaque, offset);
|
||||
ZynqSLCRState *s = opaque;
|
||||
offset /= 4;
|
||||
uint32_t ret = s->regs[offset];
|
||||
|
||||
DB_PRINT("addr: %08x data: %08x\n", (unsigned)offset, (unsigned)ret);
|
||||
if (!zynq_slcr_check_offset(offset, true)) {
|
||||
qemu_log_mask(LOG_GUEST_ERROR, "zynq_slcr: Invalid read access to "
|
||||
" addr %" HWADDR_PRIx "\n", offset * 4);
|
||||
}
|
||||
|
||||
DB_PRINT("addr: %08" HWADDR_PRIx " data: %08" PRIx32 "\n", offset * 4, ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -347,148 +357,55 @@ static void zynq_slcr_write(void *opaque, hwaddr offset,
|
||||
uint64_t val, unsigned size)
|
||||
{
|
||||
ZynqSLCRState *s = (ZynqSLCRState *)opaque;
|
||||
offset /= 4;
|
||||
|
||||
DB_PRINT("offset: %08x data: %08x\n", (unsigned)offset, (unsigned)val);
|
||||
DB_PRINT("addr: %08" HWADDR_PRIx " data: %08" PRIx64 "\n", offset * 4, val);
|
||||
|
||||
if (!zynq_slcr_check_offset(offset, false)) {
|
||||
qemu_log_mask(LOG_GUEST_ERROR, "zynq_slcr: Invalid write access to "
|
||||
"addr %" HWADDR_PRIx "\n", offset * 4);
|
||||
return;
|
||||
}
|
||||
|
||||
switch (offset) {
|
||||
case 0x00: /* SCL */
|
||||
s->scl = val & 0x1;
|
||||
return;
|
||||
case 0x4: /* SLCR_LOCK */
|
||||
case SCL:
|
||||
s->regs[SCL] = val & 0x1;
|
||||
return;
|
||||
case LOCK:
|
||||
if ((val & 0xFFFF) == XILINX_LOCK_KEY) {
|
||||
DB_PRINT("XILINX LOCK 0xF8000000 + 0x%x <= 0x%x\n", (int)offset,
|
||||
(unsigned)val & 0xFFFF);
|
||||
s->lockval = 1;
|
||||
s->regs[LOCKSTA] = 1;
|
||||
} else {
|
||||
DB_PRINT("WRONG XILINX LOCK KEY 0xF8000000 + 0x%x <= 0x%x\n",
|
||||
(int)offset, (unsigned)val & 0xFFFF);
|
||||
}
|
||||
return;
|
||||
case 0x8: /* SLCR_UNLOCK */
|
||||
case UNLOCK:
|
||||
if ((val & 0xFFFF) == XILINX_UNLOCK_KEY) {
|
||||
DB_PRINT("XILINX UNLOCK 0xF8000000 + 0x%x <= 0x%x\n", (int)offset,
|
||||
(unsigned)val & 0xFFFF);
|
||||
s->lockval = 0;
|
||||
s->regs[LOCKSTA] = 0;
|
||||
} else {
|
||||
DB_PRINT("WRONG XILINX UNLOCK KEY 0xF8000000 + 0x%x <= 0x%x\n",
|
||||
(int)offset, (unsigned)val & 0xFFFF);
|
||||
}
|
||||
return;
|
||||
case 0xc: /* LOCKSTA */
|
||||
DB_PRINT("Writing SCLR_LOCKSTA is not enabled\n");
|
||||
}
|
||||
|
||||
if (!s->regs[LOCKSTA]) {
|
||||
s->regs[offset / 4] = val;
|
||||
} else {
|
||||
DB_PRINT("SCLR registers are locked. Unlock them first\n");
|
||||
return;
|
||||
}
|
||||
|
||||
if (!s->lockval) {
|
||||
switch (offset) {
|
||||
case 0x100 ... 0x11C:
|
||||
if (offset == 0x10C) {
|
||||
goto bad_reg;
|
||||
}
|
||||
s->pll[(offset - 0x100) / 4] = val;
|
||||
break;
|
||||
case 0x120 ... 0x16C:
|
||||
s->clk[(offset - 0x120) / 4] = val;
|
||||
break;
|
||||
case 0x170 ... 0x1AC:
|
||||
s->fpga[0][(offset - 0x170) / 4] = val;
|
||||
break;
|
||||
case 0x1B0 ... 0x1D8:
|
||||
s->misc[(offset - 0x1B0) / 4] = val;
|
||||
break;
|
||||
case 0x200 ... 0x25C:
|
||||
if (offset == 0x250) {
|
||||
goto bad_reg;
|
||||
}
|
||||
s->reset[(offset - 0x200) / 4] = val;
|
||||
if (offset == 0x200 && (val & R_PSS_RST_CTRL_SOFT_RST)) {
|
||||
qemu_system_reset_request();
|
||||
}
|
||||
break;
|
||||
case 0x300:
|
||||
s->apu_ctrl = val;
|
||||
break;
|
||||
case 0x304:
|
||||
s->wdt_clk_sel = val;
|
||||
break;
|
||||
case 0x400 ... 0x408:
|
||||
s->tz_ocm[(offset - 0x400) / 4] = val;
|
||||
break;
|
||||
case 0x430:
|
||||
s->tz_ddr = val;
|
||||
break;
|
||||
case 0x440 ... 0x448:
|
||||
s->tz_dma[(offset - 0x440) / 4] = val;
|
||||
break;
|
||||
case 0x450 ... 0x458:
|
||||
s->tz_misc[(offset - 0x450) / 4] = val;
|
||||
break;
|
||||
case 0x484 ... 0x488:
|
||||
s->tz_fpga[(offset - 0x484) / 4] = val;
|
||||
break;
|
||||
case 0x500:
|
||||
s->dbg_ctrl = val;
|
||||
break;
|
||||
case 0x530:
|
||||
s->pss_idcode = val;
|
||||
break;
|
||||
case 0x600 ... 0x620:
|
||||
if (offset == 0x604) {
|
||||
goto bad_reg;
|
||||
}
|
||||
s->ddr[(offset - 0x600) / 4] = val;
|
||||
break;
|
||||
case 0x700 ... 0x7D4:
|
||||
s->mio[(offset - 0x700) / 4] = val;
|
||||
break;
|
||||
case 0x800 ... 0x810:
|
||||
s->mio_func[(offset - 0x800) / 4] = val;
|
||||
break;
|
||||
case 0x830 ... 0x834:
|
||||
s->sd[(offset - 0x830) / 4] = val;
|
||||
break;
|
||||
case 0x900:
|
||||
s->lvl_shftr_en = val;
|
||||
break;
|
||||
case 0x910:
|
||||
break;
|
||||
case 0xA00 ... 0xA1C:
|
||||
s->cpu_ram[(offset - 0xA00) / 4] = val;
|
||||
break;
|
||||
case 0xA30 ... 0xA48:
|
||||
s->iou[(offset - 0xA30) / 4] = val;
|
||||
break;
|
||||
case 0xA50:
|
||||
s->dmac_ram = val;
|
||||
break;
|
||||
case 0xA60 ... 0xA8C:
|
||||
s->afi[0][(offset - 0xA60) / 4] = val;
|
||||
break;
|
||||
case 0xA90:
|
||||
s->ocm[0] = val;
|
||||
break;
|
||||
case 0xAA0:
|
||||
s->devci_ram = val;
|
||||
break;
|
||||
case 0xAB0:
|
||||
s->csg_ram = val;
|
||||
break;
|
||||
case 0xB00 ... 0xB2C:
|
||||
if (offset == 0xB20 || offset == 0xB2C) {
|
||||
goto bad_reg;
|
||||
}
|
||||
s->gpiob[(offset - 0xB00) / 4] = val;
|
||||
break;
|
||||
case 0xB40 ... 0xB74:
|
||||
s->ddriob[(offset - 0xB40) / 4] = val;
|
||||
break;
|
||||
default:
|
||||
bad_reg:
|
||||
DB_PRINT("Bad register write %x <= %08x\n", (int)offset,
|
||||
(unsigned)val);
|
||||
switch (offset) {
|
||||
case PSS_RST_CTRL:
|
||||
if (val & R_PSS_RST_CTRL_SOFT_RST) {
|
||||
qemu_system_reset_request();
|
||||
}
|
||||
} else {
|
||||
DB_PRINT("SCLR registers are locked. Unlock them first\n");
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -498,23 +415,22 @@ static const MemoryRegionOps slcr_ops = {
|
||||
.endianness = DEVICE_NATIVE_ENDIAN,
|
||||
};
|
||||
|
||||
static int zynq_slcr_init(SysBusDevice *dev)
|
||||
static void zynq_slcr_init(Object *obj)
|
||||
{
|
||||
ZynqSLCRState *s = ZYNQ_SLCR(dev);
|
||||
ZynqSLCRState *s = ZYNQ_SLCR(obj);
|
||||
|
||||
memory_region_init_io(&s->iomem, OBJECT(s), &slcr_ops, s, "slcr", 0x1000);
|
||||
sysbus_init_mmio(dev, &s->iomem);
|
||||
|
||||
return 0;
|
||||
memory_region_init_io(&s->iomem, obj, &slcr_ops, s, "slcr",
|
||||
ZYNQ_SLCR_MMIO_SIZE);
|
||||
sysbus_init_mmio(SYS_BUS_DEVICE(obj), &s->iomem);
|
||||
}
|
||||
|
||||
static const VMStateDescription vmstate_zynq_slcr = {
|
||||
.name = "zynq_slcr",
|
||||
.version_id = 1,
|
||||
.minimum_version_id = 1,
|
||||
.minimum_version_id_old = 1,
|
||||
.version_id = 2,
|
||||
.minimum_version_id = 2,
|
||||
.minimum_version_id_old = 2,
|
||||
.fields = (VMStateField[]) {
|
||||
VMSTATE_UINT8_ARRAY(data, ZynqSLCRState, 0x1000),
|
||||
VMSTATE_UINT32_ARRAY(regs, ZynqSLCRState, ZYNQ_SLCR_NUM_REGS),
|
||||
VMSTATE_END_OF_LIST()
|
||||
}
|
||||
};
|
||||
@@ -522,9 +438,7 @@ static const VMStateDescription vmstate_zynq_slcr = {
|
||||
static void zynq_slcr_class_init(ObjectClass *klass, void *data)
|
||||
{
|
||||
DeviceClass *dc = DEVICE_CLASS(klass);
|
||||
SysBusDeviceClass *sdc = SYS_BUS_DEVICE_CLASS(klass);
|
||||
|
||||
sdc->init = zynq_slcr_init;
|
||||
dc->vmsd = &vmstate_zynq_slcr;
|
||||
dc->reset = zynq_slcr_reset;
|
||||
}
|
||||
@@ -534,6 +448,7 @@ static const TypeInfo zynq_slcr_info = {
|
||||
.name = TYPE_ZYNQ_SLCR,
|
||||
.parent = TYPE_SYS_BUS_DEVICE,
|
||||
.instance_size = sizeof(ZynqSLCRState),
|
||||
.instance_init = zynq_slcr_init,
|
||||
};
|
||||
|
||||
static void zynq_slcr_register_types(void)
|
||||
|
@@ -27,11 +27,11 @@ static uint8_t padding[60];
|
||||
static void mii_set_link(RTL8201CPState *mii, bool link_ok)
|
||||
{
|
||||
if (link_ok) {
|
||||
mii->bmsr |= MII_BMSR_LINK_ST;
|
||||
mii->bmsr |= MII_BMSR_LINK_ST | MII_BMSR_AN_COMP;
|
||||
mii->anlpar |= MII_ANAR_TXFD | MII_ANAR_10FD | MII_ANAR_10 |
|
||||
MII_ANAR_CSMACD;
|
||||
} else {
|
||||
mii->bmsr &= ~MII_BMSR_LINK_ST;
|
||||
mii->bmsr &= ~(MII_BMSR_LINK_ST | MII_BMSR_AN_COMP);
|
||||
mii->anlpar = MII_ANAR_TX;
|
||||
}
|
||||
}
|
||||
@@ -391,9 +391,11 @@ static void aw_emac_write(void *opaque, hwaddr offset, uint64_t value,
|
||||
break;
|
||||
case EMAC_INT_CTL_REG:
|
||||
s->int_ctl = value;
|
||||
aw_emac_update_irq(s);
|
||||
break;
|
||||
case EMAC_INT_STA_REG:
|
||||
s->int_sta &= ~value;
|
||||
aw_emac_update_irq(s);
|
||||
break;
|
||||
case EMAC_MAC_MADR_REG:
|
||||
s->phy_target = value;
|
||||
|
@@ -1093,7 +1093,7 @@ static uint64_t gem_read(void *opaque, hwaddr offset, unsigned size)
|
||||
uint32_t phy_addr, reg_num;
|
||||
|
||||
phy_addr = (retval & GEM_PHYMNTNC_ADDR) >> GEM_PHYMNTNC_ADDR_SHFT;
|
||||
if (phy_addr == BOARD_PHY_ADDRESS) {
|
||||
if (phy_addr == BOARD_PHY_ADDRESS || phy_addr == 0) {
|
||||
reg_num = (retval & GEM_PHYMNTNC_REG) >> GEM_PHYMNTNC_REG_SHIFT;
|
||||
retval &= 0xFFFF0000;
|
||||
retval |= gem_phy_read(s, reg_num);
|
||||
@@ -1193,7 +1193,7 @@ static void gem_write(void *opaque, hwaddr offset, uint64_t val,
|
||||
uint32_t phy_addr, reg_num;
|
||||
|
||||
phy_addr = (val & GEM_PHYMNTNC_ADDR) >> GEM_PHYMNTNC_ADDR_SHFT;
|
||||
if (phy_addr == BOARD_PHY_ADDRESS) {
|
||||
if (phy_addr == BOARD_PHY_ADDRESS || phy_addr == 0) {
|
||||
reg_num = (val & GEM_PHYMNTNC_REG) >> GEM_PHYMNTNC_REG_SHIFT;
|
||||
gem_phy_write(s, reg_num, val);
|
||||
}
|
||||
|
@@ -718,7 +718,6 @@ static void pcnet_s_reset(PCNetState *s)
|
||||
s->csr[94] = 0x0000;
|
||||
s->csr[100] = 0x0200;
|
||||
s->csr[103] = 0x0105;
|
||||
s->csr[103] = 0x0105;
|
||||
s->csr[112] = 0x0000;
|
||||
s->csr[114] = 0x0000;
|
||||
s->csr[122] = 0x0000;
|
||||
|
@@ -98,7 +98,7 @@ static unsigned int tdk_read(struct PHY *phy, unsigned int req)
|
||||
r |= 1;
|
||||
break;
|
||||
case 17:
|
||||
/* Marvel PHY on many xilinx boards. */
|
||||
/* Marvell PHY on many xilinx boards. */
|
||||
r = 0x8000; /* 1000Mb */
|
||||
break;
|
||||
case 18:
|
||||
@@ -142,6 +142,9 @@ tdk_write(struct PHY *phy, unsigned int req, unsigned int data)
|
||||
phy->regs[regnum] = data;
|
||||
break;
|
||||
}
|
||||
|
||||
/* Unconditionally clear regs[BMCR][BMCR_RESET] */
|
||||
phy->regs[0] &= ~0x8000;
|
||||
}
|
||||
|
||||
static void
|
||||
|
@@ -19,6 +19,15 @@
|
||||
#include "sysemu/sysemu.h"
|
||||
#include "hw/timer/allwinner-a10-pit.h"
|
||||
|
||||
static void a10_pit_update_irq(AwA10PITState *s)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < AW_A10_PIT_TIMER_NR; i++) {
|
||||
qemu_set_irq(s->irq[i], !!(s->irq_status & s->irq_enable & (1 << i)));
|
||||
}
|
||||
}
|
||||
|
||||
static uint64_t a10_pit_read(void *opaque, hwaddr offset, unsigned size)
|
||||
{
|
||||
AwA10PITState *s = AW_A10_PIT(opaque);
|
||||
@@ -65,6 +74,22 @@ static uint64_t a10_pit_read(void *opaque, hwaddr offset, unsigned size)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void a10_pit_set_freq(AwA10PITState *s, int index)
|
||||
{
|
||||
uint32_t prescaler, source, source_freq;
|
||||
|
||||
prescaler = 1 << extract32(s->control[index], 4, 3);
|
||||
source = extract32(s->control[index], 2, 2);
|
||||
source_freq = s->clk_freq[source];
|
||||
|
||||
if (source_freq) {
|
||||
ptimer_set_freq(s->timer[index], source_freq / prescaler);
|
||||
} else {
|
||||
qemu_log_mask(LOG_GUEST_ERROR, "%s: Invalid clock source %u\n",
|
||||
__func__, source);
|
||||
}
|
||||
}
|
||||
|
||||
static void a10_pit_write(void *opaque, hwaddr offset, uint64_t value,
|
||||
unsigned size)
|
||||
{
|
||||
@@ -74,9 +99,11 @@ static void a10_pit_write(void *opaque, hwaddr offset, uint64_t value,
|
||||
switch (offset) {
|
||||
case AW_A10_PIT_TIMER_IRQ_EN:
|
||||
s->irq_enable = value;
|
||||
a10_pit_update_irq(s);
|
||||
break;
|
||||
case AW_A10_PIT_TIMER_IRQ_ST:
|
||||
s->irq_status &= ~value;
|
||||
a10_pit_update_irq(s);
|
||||
break;
|
||||
case AW_A10_PIT_TIMER_BASE ... AW_A10_PIT_TIMER_BASE_END:
|
||||
index = offset & 0xf0;
|
||||
@@ -85,6 +112,7 @@ static void a10_pit_write(void *opaque, hwaddr offset, uint64_t value,
|
||||
switch (offset & 0x0f) {
|
||||
case AW_A10_PIT_TIMER_CONTROL:
|
||||
s->control[index] = value;
|
||||
a10_pit_set_freq(s, index);
|
||||
if (s->control[index] & AW_A10_PIT_TIMER_RELOAD) {
|
||||
ptimer_set_count(s->timer[index], s->interval[index]);
|
||||
}
|
||||
@@ -150,6 +178,14 @@ static const MemoryRegionOps a10_pit_ops = {
|
||||
.endianness = DEVICE_NATIVE_ENDIAN,
|
||||
};
|
||||
|
||||
static Property a10_pit_properties[] = {
|
||||
DEFINE_PROP_UINT32("clk0-freq", AwA10PITState, clk_freq[0], 0),
|
||||
DEFINE_PROP_UINT32("clk1-freq", AwA10PITState, clk_freq[1], 0),
|
||||
DEFINE_PROP_UINT32("clk2-freq", AwA10PITState, clk_freq[2], 0),
|
||||
DEFINE_PROP_UINT32("clk3-freq", AwA10PITState, clk_freq[3], 0),
|
||||
DEFINE_PROP_END_OF_LIST(),
|
||||
};
|
||||
|
||||
static const VMStateDescription vmstate_a10_pit = {
|
||||
.name = "a10.pit",
|
||||
.version_id = 1,
|
||||
@@ -178,11 +214,14 @@ static void a10_pit_reset(DeviceState *dev)
|
||||
|
||||
s->irq_enable = 0;
|
||||
s->irq_status = 0;
|
||||
a10_pit_update_irq(s);
|
||||
|
||||
for (i = 0; i < 6; i++) {
|
||||
s->control[i] = AW_A10_PIT_DEFAULT_CLOCK;
|
||||
s->interval[i] = 0;
|
||||
s->count[i] = 0;
|
||||
ptimer_stop(s->timer[i]);
|
||||
a10_pit_set_freq(s, i);
|
||||
}
|
||||
s->watch_dog_mode = 0;
|
||||
s->watch_dog_control = 0;
|
||||
@@ -193,18 +232,17 @@ static void a10_pit_reset(DeviceState *dev)
|
||||
|
||||
static void a10_pit_timer_cb(void *opaque)
|
||||
{
|
||||
AwA10PITState *s = AW_A10_PIT(opaque);
|
||||
uint8_t i;
|
||||
AwA10TimerContext *tc = opaque;
|
||||
AwA10PITState *s = tc->container;
|
||||
uint8_t i = tc->index;
|
||||
|
||||
for (i = 0; i < AW_A10_PIT_TIMER_NR; i++) {
|
||||
if (s->control[i] & AW_A10_PIT_TIMER_EN) {
|
||||
s->irq_status |= 1 << i;
|
||||
if (s->control[i] & AW_A10_PIT_TIMER_MODE) {
|
||||
ptimer_stop(s->timer[i]);
|
||||
s->control[i] &= ~AW_A10_PIT_TIMER_EN;
|
||||
}
|
||||
qemu_irq_pulse(s->irq[i]);
|
||||
if (s->control[i] & AW_A10_PIT_TIMER_EN) {
|
||||
s->irq_status |= 1 << i;
|
||||
if (s->control[i] & AW_A10_PIT_TIMER_MODE) {
|
||||
ptimer_stop(s->timer[i]);
|
||||
s->control[i] &= ~AW_A10_PIT_TIMER_EN;
|
||||
}
|
||||
a10_pit_update_irq(s);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -223,9 +261,12 @@ static void a10_pit_init(Object *obj)
|
||||
sysbus_init_mmio(sbd, &s->iomem);
|
||||
|
||||
for (i = 0; i < AW_A10_PIT_TIMER_NR; i++) {
|
||||
bh[i] = qemu_bh_new(a10_pit_timer_cb, s);
|
||||
AwA10TimerContext *tc = &s->timer_context[i];
|
||||
|
||||
tc->container = s;
|
||||
tc->index = i;
|
||||
bh[i] = qemu_bh_new(a10_pit_timer_cb, tc);
|
||||
s->timer[i] = ptimer_init(bh[i]);
|
||||
ptimer_set_freq(s->timer[i], 240000);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -234,6 +275,7 @@ static void a10_pit_class_init(ObjectClass *klass, void *data)
|
||||
DeviceClass *dc = DEVICE_CLASS(klass);
|
||||
|
||||
dc->reset = a10_pit_reset;
|
||||
dc->props = a10_pit_properties;
|
||||
dc->desc = "allwinner a10 timer";
|
||||
dc->vmsd = &vmstate_a10_pit;
|
||||
}
|
||||
|
@@ -346,11 +346,13 @@ static void cadence_ttc_write(void *opaque, hwaddr offset,
|
||||
case 0x34:
|
||||
case 0x38:
|
||||
s->reg_match[0] = value & 0xffff;
|
||||
break;
|
||||
|
||||
case 0x3c: /* match register */
|
||||
case 0x40:
|
||||
case 0x44:
|
||||
s->reg_match[1] = value & 0xffff;
|
||||
break;
|
||||
|
||||
case 0x48: /* match register */
|
||||
case 0x4c:
|
||||
|
@@ -26,6 +26,10 @@ common-obj-y += ccid-card-passthru.o
|
||||
common-obj-$(CONFIG_SMARTCARD_NSS) += ccid-card-emulated.o
|
||||
endif
|
||||
|
||||
ifeq ($(CONFIG_POSIX),y)
|
||||
common-obj-$(CONFIG_USB_STORAGE_MTP) += dev-mtp.o
|
||||
endif
|
||||
|
||||
# usb redirection
|
||||
common-obj-$(CONFIG_USB_REDIR) += redirect.o quirks.o
|
||||
|
||||
|
@@ -44,7 +44,7 @@ typedef struct msos_compat_hdr {
|
||||
typedef struct msos_compat_func {
|
||||
uint8_t bFirstInterfaceNumber;
|
||||
uint8_t reserved_1;
|
||||
uint8_t compatibleId[8];
|
||||
char compatibleId[8];
|
||||
uint8_t subCompatibleId[8];
|
||||
uint8_t reserved_2[6];
|
||||
} QEMU_PACKED msos_compat_func;
|
||||
@@ -59,6 +59,10 @@ static int usb_desc_msos_compat(const USBDesc *desc, uint8_t *dest)
|
||||
func = (void *)(dest + length);
|
||||
func->bFirstInterfaceNumber = 0;
|
||||
func->reserved_1 = 0x01;
|
||||
if (desc->msos->CompatibleID) {
|
||||
snprintf(func->compatibleId, sizeof(func->compatibleId),
|
||||
"%s", desc->msos->CompatibleID);
|
||||
}
|
||||
length += sizeof(*func);
|
||||
count++;
|
||||
|
||||
|
@@ -184,6 +184,7 @@ struct USBDescOther {
|
||||
};
|
||||
|
||||
struct USBDescMSOS {
|
||||
const char *CompatibleID;
|
||||
const wchar_t *Label;
|
||||
bool SelectiveSuspendEnabled;
|
||||
};
|
||||
|
1103
hw/usb/dev-mtp.c
Normal file
1103
hw/usb/dev-mtp.c
Normal file
File diff suppressed because it is too large
Load Diff
@@ -180,7 +180,7 @@ int bdrv_create(BlockDriver *drv, const char* filename,
|
||||
QEMUOptionParameter *options, Error **errp);
|
||||
int bdrv_create_file(const char* filename, QEMUOptionParameter *options,
|
||||
Error **errp);
|
||||
BlockDriverState *bdrv_new(const char *device_name);
|
||||
BlockDriverState *bdrv_new(const char *device_name, Error **errp);
|
||||
void bdrv_make_anon(BlockDriverState *bs);
|
||||
void bdrv_swap(BlockDriverState *bs_new, BlockDriverState *bs_old);
|
||||
void bdrv_append(BlockDriverState *bs_new, BlockDriverState *bs_top);
|
||||
@@ -429,7 +429,8 @@ bool bdrv_qiov_is_aligned(BlockDriverState *bs, QEMUIOVector *qiov);
|
||||
|
||||
struct HBitmapIter;
|
||||
typedef struct BdrvDirtyBitmap BdrvDirtyBitmap;
|
||||
BdrvDirtyBitmap *bdrv_create_dirty_bitmap(BlockDriverState *bs, int granularity);
|
||||
BdrvDirtyBitmap *bdrv_create_dirty_bitmap(BlockDriverState *bs, int granularity,
|
||||
Error **errp);
|
||||
void bdrv_release_dirty_bitmap(BlockDriverState *bs, BdrvDirtyBitmap *bitmap);
|
||||
BlockDirtyInfoList *bdrv_query_dirty_bitmaps(BlockDriverState *bs);
|
||||
int bdrv_get_dirty(BlockDriverState *bs, BdrvDirtyBitmap *bitmap, int64_t sector);
|
||||
|
@@ -162,3 +162,55 @@
|
||||
#define stw(p, v) stw_data(p, v)
|
||||
#define stl(p, v) stl_data(p, v)
|
||||
#define stq(p, v) stq_data(p, v)
|
||||
|
||||
/**
|
||||
* tlb_vaddr_to_host:
|
||||
* @env: CPUArchState
|
||||
* @addr: guest virtual address to look up
|
||||
* @access_type: 0 for read, 1 for write, 2 for execute
|
||||
* @mmu_idx: MMU index to use for lookup
|
||||
*
|
||||
* Look up the specified guest virtual index in the TCG softmmu TLB.
|
||||
* If the TLB contains a host virtual address suitable for direct RAM
|
||||
* access, then return it. Otherwise (TLB miss, TLB entry is for an
|
||||
* I/O access, etc) return NULL.
|
||||
*
|
||||
* This is the equivalent of the initial fast-path code used by
|
||||
* TCG backends for guest load and store accesses.
|
||||
*/
|
||||
static inline void *tlb_vaddr_to_host(CPUArchState *env, target_ulong addr,
|
||||
int access_type, int mmu_idx)
|
||||
{
|
||||
int index = (addr >> TARGET_PAGE_BITS) & (CPU_TLB_SIZE - 1);
|
||||
CPUTLBEntry *tlbentry = &env->tlb_table[mmu_idx][index];
|
||||
target_ulong tlb_addr;
|
||||
uintptr_t haddr;
|
||||
|
||||
switch (access_type) {
|
||||
case 0:
|
||||
tlb_addr = tlbentry->addr_read;
|
||||
break;
|
||||
case 1:
|
||||
tlb_addr = tlbentry->addr_write;
|
||||
break;
|
||||
case 2:
|
||||
tlb_addr = tlbentry->addr_code;
|
||||
break;
|
||||
default:
|
||||
g_assert_not_reached();
|
||||
}
|
||||
|
||||
if ((addr & TARGET_PAGE_MASK)
|
||||
!= (tlb_addr & (TARGET_PAGE_MASK | TLB_INVALID_MASK))) {
|
||||
/* TLB entry is for a different page */
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (tlb_addr & ~TARGET_PAGE_MASK) {
|
||||
/* IO access */
|
||||
return NULL;
|
||||
}
|
||||
|
||||
haddr = addr + env->tlb_table[mmu_idx][index].addend;
|
||||
return (void *)haddr;
|
||||
}
|
||||
|
@@ -144,6 +144,7 @@
|
||||
#define MII_BMSR_10T_FD (1 << 12)
|
||||
#define MII_BMSR_10T_HD (1 << 11)
|
||||
#define MII_BMSR_MFPS (1 << 6)
|
||||
#define MII_BMSR_AN_COMP (1 << 5)
|
||||
#define MII_BMSR_AUTONEG (1 << 3)
|
||||
#define MII_BMSR_LINK_ST (1 << 2)
|
||||
|
||||
|
@@ -35,13 +35,22 @@
|
||||
|
||||
#define AW_A10_PIT_DEFAULT_CLOCK 0x4
|
||||
|
||||
typedef struct AwA10PITState {
|
||||
typedef struct AwA10PITState AwA10PITState;
|
||||
|
||||
typedef struct AwA10TimerContext {
|
||||
AwA10PITState *container;
|
||||
int index;
|
||||
} AwA10TimerContext;
|
||||
|
||||
struct AwA10PITState {
|
||||
/*< private >*/
|
||||
SysBusDevice parent_obj;
|
||||
/*< public >*/
|
||||
qemu_irq irq[AW_A10_PIT_TIMER_NR];
|
||||
ptimer_state * timer[AW_A10_PIT_TIMER_NR];
|
||||
AwA10TimerContext timer_context[AW_A10_PIT_TIMER_NR];
|
||||
MemoryRegion iomem;
|
||||
uint32_t clk_freq[4];
|
||||
|
||||
uint32_t irq_enable;
|
||||
uint32_t irq_status;
|
||||
@@ -53,6 +62,6 @@ typedef struct AwA10PITState {
|
||||
uint32_t count_lo;
|
||||
uint32_t count_hi;
|
||||
uint32_t count_ctl;
|
||||
} AwA10PITState;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@@ -79,7 +79,6 @@ int monitor_handle_fd_param(Monitor *mon, const char *fdname);
|
||||
void monitor_vprintf(Monitor *mon, const char *fmt, va_list ap)
|
||||
GCC_FMT_ATTR(2, 0);
|
||||
void monitor_printf(Monitor *mon, const char *fmt, ...) GCC_FMT_ATTR(2, 3);
|
||||
void monitor_print_filename(Monitor *mon, const char *filename);
|
||||
void monitor_flush(Monitor *mon);
|
||||
int monitor_set_cpu(int cpu_index);
|
||||
int monitor_get_cpu_index(void);
|
||||
|
@@ -12,7 +12,6 @@
|
||||
#ifndef QERROR_H
|
||||
#define QERROR_H
|
||||
|
||||
#include "qapi/qmp/qdict.h"
|
||||
#include "qapi/qmp/qstring.h"
|
||||
#include "qemu/error-report.h"
|
||||
#include "qapi/error.h"
|
||||
@@ -35,51 +34,30 @@ void qerror_report_err(Error *err);
|
||||
* Please keep the definitions in alphabetical order.
|
||||
* Use scripts/check-qerror.sh to check.
|
||||
*/
|
||||
#define QERR_ADD_CLIENT_FAILED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Could not add client"
|
||||
|
||||
#define QERR_AMBIGUOUS_PATH \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Path '%s' does not uniquely identify an object"
|
||||
|
||||
#define QERR_BAD_BUS_FOR_DEVICE \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Device '%s' can't go on a %s bus"
|
||||
|
||||
#define QERR_BASE_NOT_FOUND \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Base '%s' not found"
|
||||
|
||||
#define QERR_BLOCK_JOB_NOT_ACTIVE \
|
||||
ERROR_CLASS_DEVICE_NOT_ACTIVE, "No active block job on device '%s'"
|
||||
|
||||
#define QERR_BLOCK_JOB_PAUSED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "The block job for device '%s' is currently paused"
|
||||
|
||||
#define QERR_BLOCK_JOB_NOT_READY \
|
||||
ERROR_CLASS_GENERIC_ERROR, "The active block job for device '%s' cannot be completed"
|
||||
|
||||
#define QERR_BLOCK_FORMAT_FEATURE_NOT_SUPPORTED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Block format '%s' used by device '%s' does not support feature '%s'"
|
||||
|
||||
#define QERR_BUFFER_OVERRUN \
|
||||
ERROR_CLASS_GENERIC_ERROR, "An internal buffer overran"
|
||||
|
||||
#define QERR_BUS_NO_HOTPLUG \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Bus '%s' does not support hotplugging"
|
||||
|
||||
#define QERR_BUS_NOT_FOUND \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Bus '%s' not found"
|
||||
|
||||
#define QERR_COMMAND_DISABLED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "The command %s has been disabled for this instance"
|
||||
|
||||
#define QERR_COMMAND_NOT_FOUND \
|
||||
ERROR_CLASS_COMMAND_NOT_FOUND, "The command %s has not been found"
|
||||
|
||||
#define QERR_DEVICE_ENCRYPTED \
|
||||
ERROR_CLASS_DEVICE_ENCRYPTED, "'%s' (%s) is encrypted"
|
||||
|
||||
#define QERR_DEVICE_FEATURE_BLOCKS_MIGRATION \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Migration is disabled when using feature '%s' in device '%s'"
|
||||
|
||||
#define QERR_DEVICE_HAS_NO_MEDIUM \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Device '%s' has no medium"
|
||||
|
||||
@@ -92,15 +70,6 @@ void qerror_report_err(Error *err);
|
||||
#define QERR_DEVICE_IS_READ_ONLY \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Device '%s' is read only"
|
||||
|
||||
#define QERR_DEVICE_LOCKED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Device '%s' is locked"
|
||||
|
||||
#define QERR_DEVICE_MULTIPLE_BUSSES \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Device '%s' has multiple child busses"
|
||||
|
||||
#define QERR_DEVICE_NO_BUS \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Device '%s' has no child bus"
|
||||
|
||||
#define QERR_DEVICE_NO_HOTPLUG \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Device '%s' does not support hotplugging"
|
||||
|
||||
@@ -113,12 +82,6 @@ void qerror_report_err(Error *err);
|
||||
#define QERR_DEVICE_NOT_FOUND \
|
||||
ERROR_CLASS_DEVICE_NOT_FOUND, "Device '%s' not found"
|
||||
|
||||
#define QERR_DEVICE_NOT_REMOVABLE \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Device '%s' is not removable"
|
||||
|
||||
#define QERR_DUPLICATE_ID \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Duplicate ID '%s' for %s"
|
||||
|
||||
#define QERR_FD_NOT_FOUND \
|
||||
ERROR_CLASS_GENERIC_ERROR, "File descriptor named '%s' not found"
|
||||
|
||||
@@ -131,15 +94,9 @@ void qerror_report_err(Error *err);
|
||||
#define QERR_INVALID_BLOCK_FORMAT \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Invalid block format '%s'"
|
||||
|
||||
#define QERR_INVALID_OPTION_GROUP \
|
||||
ERROR_CLASS_GENERIC_ERROR, "There is no option group '%s'"
|
||||
|
||||
#define QERR_INVALID_PARAMETER \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Invalid parameter '%s'"
|
||||
|
||||
#define QERR_INVALID_PARAMETER_COMBINATION \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Invalid parameter combination"
|
||||
|
||||
#define QERR_INVALID_PARAMETER_TYPE \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Invalid parameter type for '%s', expected: %s"
|
||||
|
||||
@@ -152,9 +109,6 @@ void qerror_report_err(Error *err);
|
||||
#define QERR_IO_ERROR \
|
||||
ERROR_CLASS_GENERIC_ERROR, "An IO error has occurred"
|
||||
|
||||
#define QERR_JSON_PARSE_ERROR \
|
||||
ERROR_CLASS_GENERIC_ERROR, "JSON parse error, %s"
|
||||
|
||||
#define QERR_JSON_PARSING \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Invalid JSON syntax"
|
||||
|
||||
@@ -164,45 +118,21 @@ void qerror_report_err(Error *err);
|
||||
#define QERR_MIGRATION_ACTIVE \
|
||||
ERROR_CLASS_GENERIC_ERROR, "There's a migration process in progress"
|
||||
|
||||
#define QERR_MIGRATION_NOT_SUPPORTED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "State blocked by non-migratable device '%s'"
|
||||
|
||||
#define QERR_MISSING_PARAMETER \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Parameter '%s' is missing"
|
||||
|
||||
#define QERR_NO_BUS_FOR_DEVICE \
|
||||
ERROR_CLASS_GENERIC_ERROR, "No '%s' bus found for device '%s'"
|
||||
|
||||
#define QERR_NOT_SUPPORTED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Not supported"
|
||||
|
||||
#define QERR_PERMISSION_DENIED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Insufficient permission to perform this operation"
|
||||
|
||||
#define QERR_PROPERTY_NOT_FOUND \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Property '%s.%s' not found"
|
||||
|
||||
#define QERR_PROPERTY_VALUE_BAD \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Property '%s.%s' doesn't take value '%s'"
|
||||
|
||||
#define QERR_PROPERTY_VALUE_IN_USE \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Property '%s.%s' can't take value '%s', it's in use"
|
||||
|
||||
#define QERR_PROPERTY_VALUE_NOT_FOUND \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Property '%s.%s' can't find value '%s'"
|
||||
|
||||
#define QERR_PROPERTY_VALUE_NOT_POWER_OF_2 \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Property %s.%s doesn't take value '%" PRId64 "', it's not a power of 2"
|
||||
|
||||
#define QERR_PROPERTY_VALUE_OUT_OF_RANGE \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Property %s.%s doesn't take value %" PRId64 " (minimum: %" PRId64 ", maximum: %" PRId64 ")"
|
||||
|
||||
#define QERR_QGA_COMMAND_FAILED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Guest agent command failed, error was '%s'"
|
||||
|
||||
#define QERR_QGA_LOGGING_FAILED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Guest agent failed to log non-optional log statement"
|
||||
|
||||
#define QERR_QMP_BAD_INPUT_OBJECT \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Expected '%s' in QMP input"
|
||||
|
||||
@@ -212,15 +142,9 @@ void qerror_report_err(Error *err);
|
||||
#define QERR_QMP_EXTRA_MEMBER \
|
||||
ERROR_CLASS_GENERIC_ERROR, "QMP input object member '%s' is unexpected"
|
||||
|
||||
#define QERR_RESET_REQUIRED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Resetting the Virtual Machine is required"
|
||||
|
||||
#define QERR_SET_PASSWD_FAILED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Could not set password"
|
||||
|
||||
#define QERR_TOO_MANY_FILES \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Too many open files"
|
||||
|
||||
#define QERR_UNDEFINED_ERROR \
|
||||
ERROR_CLASS_GENERIC_ERROR, "An undefined error has occurred"
|
||||
|
||||
@@ -230,9 +154,6 @@ void qerror_report_err(Error *err);
|
||||
#define QERR_UNSUPPORTED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "this feature or command is not currently supported"
|
||||
|
||||
#define QERR_VIRTFS_FEATURE_BLOCKS_MIGRATION \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Migration is disabled when VirtFS export path '%s' is mounted in the guest using mount_tag '%s'"
|
||||
|
||||
#define QERR_SOCKET_CONNECT_FAILED \
|
||||
ERROR_CLASS_GENERIC_ERROR, "Failed to connect to socket"
|
||||
|
||||
|
@@ -8,6 +8,8 @@
|
||||
|
||||
QemuOptsList *qemu_find_opts(const char *group);
|
||||
QemuOptsList *qemu_find_opts_err(const char *group, Error **errp);
|
||||
QemuOpts *qemu_find_opts_singleton(const char *group);
|
||||
|
||||
void qemu_add_opts(QemuOptsList *list);
|
||||
void qemu_add_drive_opts(QemuOptsList *list);
|
||||
int qemu_set_option(const char *str);
|
||||
|
@@ -37,7 +37,6 @@ void loc_set_file(const char *fname, int lno);
|
||||
void error_vprintf(const char *fmt, va_list ap) GCC_FMT_ATTR(1, 0);
|
||||
void error_printf(const char *fmt, ...) GCC_FMT_ATTR(1, 2);
|
||||
void error_printf_unless_qmp(const char *fmt, ...) GCC_FMT_ATTR(1, 2);
|
||||
void error_print_loc(void);
|
||||
void error_set_progname(const char *argv0);
|
||||
void error_report(const char *fmt, ...) GCC_FMT_ATTR(1, 2);
|
||||
const char *error_get_progname(void);
|
||||
|
@@ -53,7 +53,7 @@ static inline Int128 int128_rshift(Int128 a, int n)
|
||||
if (n >= 64) {
|
||||
return (Int128) { h, h >> 63 };
|
||||
} else {
|
||||
return (Int128) { (a.lo >> n) | (a.hi << (64 - n)), h };
|
||||
return (Int128) { (a.lo >> n) | ((uint64_t)a.hi << (64 - n)), h };
|
||||
}
|
||||
}
|
||||
|
||||
@@ -78,7 +78,7 @@ static inline Int128 int128_neg(Int128 a)
|
||||
|
||||
static inline Int128 int128_sub(Int128 a, Int128 b)
|
||||
{
|
||||
return (Int128){ a.lo - b.lo, a.hi - b.hi - (a.lo < b.lo) };
|
||||
return (Int128){ a.lo - b.lo, (uint64_t)a.hi - b.hi - (a.lo < b.lo) };
|
||||
}
|
||||
|
||||
static inline bool int128_nonneg(Int128 a)
|
||||
|
@@ -22,6 +22,8 @@
|
||||
#define KVM_DEV_FLIC_CLEAR_IRQS 3
|
||||
#define KVM_DEV_FLIC_APF_ENABLE 4
|
||||
#define KVM_DEV_FLIC_APF_DISABLE_WAIT 5
|
||||
#define KVM_DEV_FLIC_ADAPTER_REGISTER 6
|
||||
#define KVM_DEV_FLIC_ADAPTER_MODIFY 7
|
||||
/*
|
||||
* We can have up to 4*64k pending subchannels + 8 adapter interrupts,
|
||||
* as well as up to ASYNC_PF_PER_VCPU*KVM_MAX_VCPUS pfault done interrupts.
|
||||
@@ -32,6 +34,26 @@
|
||||
#define KVM_S390_MAX_FLOAT_IRQS 266250
|
||||
#define KVM_S390_FLIC_MAX_BUFFER 0x2000000
|
||||
|
||||
struct kvm_s390_io_adapter {
|
||||
__u32 id;
|
||||
__u8 isc;
|
||||
__u8 maskable;
|
||||
__u8 swap;
|
||||
__u8 pad;
|
||||
};
|
||||
|
||||
#define KVM_S390_IO_ADAPTER_MASK 1
|
||||
#define KVM_S390_IO_ADAPTER_MAP 2
|
||||
#define KVM_S390_IO_ADAPTER_UNMAP 3
|
||||
|
||||
struct kvm_s390_io_adapter_req {
|
||||
__u32 id;
|
||||
__u8 type;
|
||||
__u8 mask;
|
||||
__u16 pad0;
|
||||
__u64 addr;
|
||||
};
|
||||
|
||||
/* for KVM_GET_REGS and KVM_SET_REGS */
|
||||
struct kvm_regs {
|
||||
/* general purpose regs for s390 */
|
||||
@@ -76,4 +98,6 @@ struct kvm_sync_regs {
|
||||
#define KVM_REG_S390_PFTOKEN (KVM_REG_S390 | KVM_REG_SIZE_U64 | 0x5)
|
||||
#define KVM_REG_S390_PFCOMPARE (KVM_REG_S390 | KVM_REG_SIZE_U64 | 0x6)
|
||||
#define KVM_REG_S390_PFSELECT (KVM_REG_S390 | KVM_REG_SIZE_U64 | 0x7)
|
||||
#define KVM_REG_S390_PP (KVM_REG_S390 | KVM_REG_SIZE_U64 | 0x8)
|
||||
#define KVM_REG_S390_GBEA (KVM_REG_S390 | KVM_REG_SIZE_U64 | 0x9)
|
||||
#endif
|
||||
|
@@ -740,6 +740,9 @@ struct kvm_ppc_smmu_info {
|
||||
#define KVM_CAP_SPAPR_MULTITCE 94
|
||||
#define KVM_CAP_EXT_EMUL_CPUID 95
|
||||
#define KVM_CAP_HYPERV_TIME 96
|
||||
#define KVM_CAP_IOAPIC_POLARITY_IGNORED 97
|
||||
#define KVM_CAP_ENABLE_CAP_VM 98
|
||||
#define KVM_CAP_S390_IRQCHIP 99
|
||||
|
||||
#ifdef KVM_CAP_IRQ_ROUTING
|
||||
|
||||
@@ -755,9 +758,18 @@ struct kvm_irq_routing_msi {
|
||||
__u32 pad;
|
||||
};
|
||||
|
||||
struct kvm_irq_routing_s390_adapter {
|
||||
__u64 ind_addr;
|
||||
__u64 summary_addr;
|
||||
__u64 ind_offset;
|
||||
__u32 summary_offset;
|
||||
__u32 adapter_id;
|
||||
};
|
||||
|
||||
/* gsi routing entry types */
|
||||
#define KVM_IRQ_ROUTING_IRQCHIP 1
|
||||
#define KVM_IRQ_ROUTING_MSI 2
|
||||
#define KVM_IRQ_ROUTING_S390_ADAPTER 3
|
||||
|
||||
struct kvm_irq_routing_entry {
|
||||
__u32 gsi;
|
||||
@@ -767,6 +779,7 @@ struct kvm_irq_routing_entry {
|
||||
union {
|
||||
struct kvm_irq_routing_irqchip irqchip;
|
||||
struct kvm_irq_routing_msi msi;
|
||||
struct kvm_irq_routing_s390_adapter adapter;
|
||||
__u32 pad[8];
|
||||
} u;
|
||||
};
|
||||
@@ -1075,6 +1088,10 @@ struct kvm_s390_ucas_mapping {
|
||||
/* Available with KVM_CAP_DEBUGREGS */
|
||||
#define KVM_GET_DEBUGREGS _IOR(KVMIO, 0xa1, struct kvm_debugregs)
|
||||
#define KVM_SET_DEBUGREGS _IOW(KVMIO, 0xa2, struct kvm_debugregs)
|
||||
/*
|
||||
* vcpu version available with KVM_ENABLE_CAP
|
||||
* vm version available with KVM_CAP_ENABLE_CAP_VM
|
||||
*/
|
||||
#define KVM_ENABLE_CAP _IOW(KVMIO, 0xa3, struct kvm_enable_cap)
|
||||
/* Available with KVM_CAP_XSAVE */
|
||||
#define KVM_GET_XSAVE _IOR(KVMIO, 0xa4, struct kvm_xsave)
|
||||
|
@@ -23,6 +23,12 @@
|
||||
|
||||
#define VFIO_TYPE1_IOMMU 1
|
||||
#define VFIO_SPAPR_TCE_IOMMU 2
|
||||
#define VFIO_TYPE1v2_IOMMU 3
|
||||
/*
|
||||
* IOMMU enforces DMA cache coherence (ex. PCIe NoSnoop stripping). This
|
||||
* capability is subject to change as groups are added or removed.
|
||||
*/
|
||||
#define VFIO_DMA_CC_IOMMU 4
|
||||
|
||||
/*
|
||||
* The IOCTL interface is designed for extensibility by embedding the
|
||||
|
@@ -483,17 +483,17 @@ static void arm_kernel_cmpxchg64_helper(CPUARMState *env)
|
||||
addr = env->regs[2];
|
||||
|
||||
if (get_user_u64(oldval, env->regs[0])) {
|
||||
env->cp15.c6_data = env->regs[0];
|
||||
env->exception.vaddress = env->regs[0];
|
||||
goto segv;
|
||||
};
|
||||
|
||||
if (get_user_u64(newval, env->regs[1])) {
|
||||
env->cp15.c6_data = env->regs[1];
|
||||
env->exception.vaddress = env->regs[1];
|
||||
goto segv;
|
||||
};
|
||||
|
||||
if (get_user_u64(val, addr)) {
|
||||
env->cp15.c6_data = addr;
|
||||
env->exception.vaddress = addr;
|
||||
goto segv;
|
||||
}
|
||||
|
||||
@@ -501,7 +501,7 @@ static void arm_kernel_cmpxchg64_helper(CPUARMState *env)
|
||||
val = newval;
|
||||
|
||||
if (put_user_u64(val, addr)) {
|
||||
env->cp15.c6_data = addr;
|
||||
env->exception.vaddress = addr;
|
||||
goto segv;
|
||||
};
|
||||
|
||||
@@ -523,7 +523,7 @@ segv:
|
||||
info.si_errno = 0;
|
||||
/* XXX: check env->error_code */
|
||||
info.si_code = TARGET_SEGV_MAPERR;
|
||||
info._sifields._sigfault._addr = env->cp15.c6_data;
|
||||
info._sifields._sigfault._addr = env->exception.vaddress;
|
||||
queue_signal(env, info.si_signo, &info);
|
||||
|
||||
end_exclusive();
|
||||
@@ -620,14 +620,14 @@ static int do_strex(CPUARMState *env)
|
||||
abort();
|
||||
}
|
||||
if (segv) {
|
||||
env->cp15.c6_data = addr;
|
||||
env->exception.vaddress = addr;
|
||||
goto done;
|
||||
}
|
||||
if (size == 3) {
|
||||
uint32_t valhi;
|
||||
segv = get_user_u32(valhi, addr + 4);
|
||||
if (segv) {
|
||||
env->cp15.c6_data = addr + 4;
|
||||
env->exception.vaddress = addr + 4;
|
||||
goto done;
|
||||
}
|
||||
val = deposit64(val, 32, 32, valhi);
|
||||
@@ -650,14 +650,14 @@ static int do_strex(CPUARMState *env)
|
||||
break;
|
||||
}
|
||||
if (segv) {
|
||||
env->cp15.c6_data = addr;
|
||||
env->exception.vaddress = addr;
|
||||
goto done;
|
||||
}
|
||||
if (size == 3) {
|
||||
val = env->regs[(env->exclusive_info >> 12) & 0xf];
|
||||
segv = put_user_u32(val, addr + 4);
|
||||
if (segv) {
|
||||
env->cp15.c6_data = addr + 4;
|
||||
env->exception.vaddress = addr + 4;
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
@@ -832,12 +832,14 @@ void cpu_loop(CPUARMState *env)
|
||||
case EXCP_INTERRUPT:
|
||||
/* just indicate that signals should be handled asap */
|
||||
break;
|
||||
case EXCP_STREX:
|
||||
if (!do_strex(env)) {
|
||||
break;
|
||||
}
|
||||
/* fall through for segv */
|
||||
case EXCP_PREFETCH_ABORT:
|
||||
addr = env->cp15.c6_insn;
|
||||
goto do_segv;
|
||||
case EXCP_DATA_ABORT:
|
||||
addr = env->cp15.c6_data;
|
||||
do_segv:
|
||||
addr = env->exception.vaddress;
|
||||
{
|
||||
info.si_signo = SIGSEGV;
|
||||
info.si_errno = 0;
|
||||
@@ -865,12 +867,6 @@ void cpu_loop(CPUARMState *env)
|
||||
if (do_kernel_trap(env))
|
||||
goto error;
|
||||
break;
|
||||
case EXCP_STREX:
|
||||
if (do_strex(env)) {
|
||||
addr = env->cp15.c6_data;
|
||||
goto do_segv;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
error:
|
||||
fprintf(stderr, "qemu: unhandled CPU exception 0x%x - aborting\n",
|
||||
@@ -933,7 +929,7 @@ static int do_strex_a64(CPUARMState *env)
|
||||
abort();
|
||||
}
|
||||
if (segv) {
|
||||
env->cp15.c6_data = addr;
|
||||
env->exception.vaddress = addr;
|
||||
goto error;
|
||||
}
|
||||
if (val != env->exclusive_val) {
|
||||
@@ -946,7 +942,7 @@ static int do_strex_a64(CPUARMState *env)
|
||||
segv = get_user_u64(val, addr + 8);
|
||||
}
|
||||
if (segv) {
|
||||
env->cp15.c6_data = addr + (size == 2 ? 4 : 8);
|
||||
env->exception.vaddress = addr + (size == 2 ? 4 : 8);
|
||||
goto error;
|
||||
}
|
||||
if (val != env->exclusive_high) {
|
||||
@@ -981,7 +977,7 @@ static int do_strex_a64(CPUARMState *env)
|
||||
segv = put_user_u64(val, addr + 8);
|
||||
}
|
||||
if (segv) {
|
||||
env->cp15.c6_data = addr + (size == 2 ? 4 : 8);
|
||||
env->exception.vaddress = addr + (size == 2 ? 4 : 8);
|
||||
goto error;
|
||||
}
|
||||
}
|
||||
@@ -1037,12 +1033,14 @@ void cpu_loop(CPUARMState *env)
|
||||
info._sifields._sigfault._addr = env->pc;
|
||||
queue_signal(env, info.si_signo, &info);
|
||||
break;
|
||||
case EXCP_STREX:
|
||||
if (!do_strex_a64(env)) {
|
||||
break;
|
||||
}
|
||||
/* fall through for segv */
|
||||
case EXCP_PREFETCH_ABORT:
|
||||
addr = env->cp15.c6_insn;
|
||||
goto do_segv;
|
||||
case EXCP_DATA_ABORT:
|
||||
addr = env->cp15.c6_data;
|
||||
do_segv:
|
||||
addr = env->exception.vaddress;
|
||||
info.si_signo = SIGSEGV;
|
||||
info.si_errno = 0;
|
||||
/* XXX: check env->error_code */
|
||||
@@ -1060,12 +1058,6 @@ void cpu_loop(CPUARMState *env)
|
||||
queue_signal(env, info.si_signo, &info);
|
||||
}
|
||||
break;
|
||||
case EXCP_STREX:
|
||||
if (do_strex_a64(env)) {
|
||||
addr = env->cp15.c6_data;
|
||||
goto do_segv;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
fprintf(stderr, "qemu: unhandled CPU exception 0x%x - aborting\n",
|
||||
trapnr);
|
||||
|
85
monitor.c
85
monitor.c
@@ -137,6 +137,7 @@ typedef struct mon_cmd_t {
|
||||
* used, and mhandler of 1st level plays the role of help function.
|
||||
*/
|
||||
struct mon_cmd_t *sub_table;
|
||||
void (*command_completion)(ReadLineState *rs, int nb_args, const char *str);
|
||||
} mon_cmd_t;
|
||||
|
||||
/* file descriptors passed via SCM_RIGHTS */
|
||||
@@ -352,33 +353,6 @@ void monitor_printf(Monitor *mon, const char *fmt, ...)
|
||||
va_end(ap);
|
||||
}
|
||||
|
||||
void monitor_print_filename(Monitor *mon, const char *filename)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; filename[i]; i++) {
|
||||
switch (filename[i]) {
|
||||
case ' ':
|
||||
case '"':
|
||||
case '\\':
|
||||
monitor_printf(mon, "\\%c", filename[i]);
|
||||
break;
|
||||
case '\t':
|
||||
monitor_printf(mon, "\\t");
|
||||
break;
|
||||
case '\r':
|
||||
monitor_printf(mon, "\\r");
|
||||
break;
|
||||
case '\n':
|
||||
monitor_printf(mon, "\\n");
|
||||
break;
|
||||
default:
|
||||
monitor_printf(mon, "%c", filename[i]);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static int GCC_FMT_ATTR(2, 3) monitor_fprintf(FILE *stream,
|
||||
const char *fmt, ...)
|
||||
{
|
||||
@@ -2254,6 +2228,7 @@ void qmp_getfd(const char *fdname, Error **errp)
|
||||
}
|
||||
|
||||
if (qemu_isdigit(fdname[0])) {
|
||||
close(fd);
|
||||
error_set(errp, QERR_INVALID_PARAMETER_VALUE, "fdname",
|
||||
"a name not starting with a digit");
|
||||
return;
|
||||
@@ -4277,11 +4252,15 @@ static const char *next_arg_type(const char *typestr)
|
||||
return (p != NULL ? ++p : typestr);
|
||||
}
|
||||
|
||||
static void device_add_completion(ReadLineState *rs, const char *str)
|
||||
void device_add_completion(ReadLineState *rs, int nb_args, const char *str)
|
||||
{
|
||||
GSList *list, *elt;
|
||||
size_t len;
|
||||
|
||||
if (nb_args != 2) {
|
||||
return;
|
||||
}
|
||||
|
||||
len = strlen(str);
|
||||
readline_set_completion_index(rs, len);
|
||||
list = elt = object_class_get_list(TYPE_DEVICE, false);
|
||||
@@ -4290,7 +4269,9 @@ static void device_add_completion(ReadLineState *rs, const char *str)
|
||||
DeviceClass *dc = OBJECT_CLASS_CHECK(DeviceClass, elt->data,
|
||||
TYPE_DEVICE);
|
||||
name = object_class_get_name(OBJECT_CLASS(dc));
|
||||
if (!strncmp(name, str, len)) {
|
||||
|
||||
if (!dc->cannot_instantiate_with_device_add_yet
|
||||
&& !strncmp(name, str, len)) {
|
||||
readline_add_completion(rs, name);
|
||||
}
|
||||
elt = elt->next;
|
||||
@@ -4298,11 +4279,15 @@ static void device_add_completion(ReadLineState *rs, const char *str)
|
||||
g_slist_free(list);
|
||||
}
|
||||
|
||||
static void object_add_completion(ReadLineState *rs, const char *str)
|
||||
void object_add_completion(ReadLineState *rs, int nb_args, const char *str)
|
||||
{
|
||||
GSList *list, *elt;
|
||||
size_t len;
|
||||
|
||||
if (nb_args != 2) {
|
||||
return;
|
||||
}
|
||||
|
||||
len = strlen(str);
|
||||
readline_set_completion_index(rs, len);
|
||||
list = elt = object_class_get_list(TYPE_USER_CREATABLE, false);
|
||||
@@ -4318,8 +4303,8 @@ static void object_add_completion(ReadLineState *rs, const char *str)
|
||||
g_slist_free(list);
|
||||
}
|
||||
|
||||
static void device_del_completion(ReadLineState *rs, BusState *bus,
|
||||
const char *str, size_t len)
|
||||
static void device_del_bus_completion(ReadLineState *rs, BusState *bus,
|
||||
const char *str, size_t len)
|
||||
{
|
||||
BusChild *kid;
|
||||
|
||||
@@ -4332,16 +4317,32 @@ static void device_del_completion(ReadLineState *rs, BusState *bus,
|
||||
}
|
||||
|
||||
QLIST_FOREACH(dev_child, &dev->child_bus, sibling) {
|
||||
device_del_completion(rs, dev_child, str, len);
|
||||
device_del_bus_completion(rs, dev_child, str, len);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void object_del_completion(ReadLineState *rs, const char *str)
|
||||
void device_del_completion(ReadLineState *rs, int nb_args, const char *str)
|
||||
{
|
||||
size_t len;
|
||||
|
||||
if (nb_args != 2) {
|
||||
return;
|
||||
}
|
||||
|
||||
len = strlen(str);
|
||||
readline_set_completion_index(rs, len);
|
||||
device_del_bus_completion(rs, sysbus_get_default(), str, len);
|
||||
}
|
||||
|
||||
void object_del_completion(ReadLineState *rs, int nb_args, const char *str)
|
||||
{
|
||||
ObjectPropertyInfoList *list, *start;
|
||||
size_t len;
|
||||
|
||||
if (nb_args != 2) {
|
||||
return;
|
||||
}
|
||||
len = strlen(str);
|
||||
readline_set_completion_index(rs, len);
|
||||
|
||||
@@ -4395,6 +4396,9 @@ static void monitor_find_completion_by_table(Monitor *mon,
|
||||
return monitor_find_completion_by_table(mon, cmd->sub_table,
|
||||
&args[1], nb_args - 1);
|
||||
}
|
||||
if (cmd->command_completion) {
|
||||
return cmd->command_completion(mon->rs, nb_args, args[nb_args - 1]);
|
||||
}
|
||||
|
||||
ptype = next_arg_type(cmd->args_type);
|
||||
for(i = 0; i < nb_args - 2; i++) {
|
||||
@@ -4421,13 +4425,6 @@ static void monitor_find_completion_by_table(Monitor *mon,
|
||||
readline_set_completion_index(mon->rs, strlen(str));
|
||||
bdrv_iterate(block_completion_it, &mbs);
|
||||
break;
|
||||
case 'O':
|
||||
if (!strcmp(cmd->name, "device_add") && nb_args == 2) {
|
||||
device_add_completion(mon->rs, str);
|
||||
} else if (!strcmp(cmd->name, "object_add") && nb_args == 2) {
|
||||
object_add_completion(mon->rs, str);
|
||||
}
|
||||
break;
|
||||
case 's':
|
||||
case 'S':
|
||||
if (!strcmp(cmd->name, "sendkey")) {
|
||||
@@ -4441,12 +4438,6 @@ static void monitor_find_completion_by_table(Monitor *mon,
|
||||
} else if (!strcmp(cmd->name, "help|?")) {
|
||||
monitor_find_completion_by_table(mon, cmd_table,
|
||||
&args[1], nb_args - 1);
|
||||
} else if (!strcmp(cmd->name, "device_del") && nb_args == 2) {
|
||||
size_t len = strlen(str);
|
||||
readline_set_completion_index(mon->rs, len);
|
||||
device_del_completion(mon->rs, sysbus_get_default(), str, len);
|
||||
} else if (!strcmp(cmd->name, "object_del") && nb_args == 2) {
|
||||
object_del_completion(mon->rs, str);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
|
14
net/net.c
14
net/net.c
@@ -473,7 +473,7 @@ ssize_t qemu_deliver_packet(NetClientState *sender,
|
||||
|
||||
if (ret == 0) {
|
||||
nc->receive_disabled = 1;
|
||||
};
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
@@ -952,10 +952,12 @@ void net_host_device_remove(Monitor *mon, const QDict *qdict)
|
||||
|
||||
nc = net_hub_find_client_by_name(vlan_id, device);
|
||||
if (!nc) {
|
||||
error_report("Host network device '%s' on hub '%d' not found",
|
||||
device, vlan_id);
|
||||
return;
|
||||
}
|
||||
if (!net_host_check_device(nc->model)) {
|
||||
monitor_printf(mon, "invalid host network device %s\n", device);
|
||||
error_report("invalid host network device '%s'", device);
|
||||
return;
|
||||
}
|
||||
qemu_del_net_client(nc);
|
||||
@@ -1043,7 +1045,7 @@ RxFilterInfoList *qmp_query_rx_filter(bool has_name, const char *name,
|
||||
if (nc->info->type != NET_CLIENT_OPTIONS_KIND_NIC) {
|
||||
if (has_name) {
|
||||
error_setg(errp, "net client(%s) isn't a NIC", name);
|
||||
break;
|
||||
return NULL;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
@@ -1062,11 +1064,15 @@ RxFilterInfoList *qmp_query_rx_filter(bool has_name, const char *name,
|
||||
} else if (has_name) {
|
||||
error_setg(errp, "net client(%s) doesn't support"
|
||||
" rx-filter querying", name);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (has_name) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (filter_list == NULL && !error_is_set(errp) && has_name) {
|
||||
if (filter_list == NULL && has_name) {
|
||||
error_setg(errp, "invalid net client name: %s", name);
|
||||
}
|
||||
|
||||
|
@@ -527,6 +527,7 @@ static int slirp_smb(SlirpState* s, const char *exported_dir,
|
||||
"pid directory=%s\n"
|
||||
"lock directory=%s\n"
|
||||
"state directory=%s\n"
|
||||
"ncalrpc dir=%s/ncalrpc\n"
|
||||
"log file=%s/log.smbd\n"
|
||||
"smb passwd file=%s/smbpasswd\n"
|
||||
"security = user\n"
|
||||
@@ -542,6 +543,7 @@ static int slirp_smb(SlirpState* s, const char *exported_dir,
|
||||
s->smb_dir,
|
||||
s->smb_dir,
|
||||
s->smb_dir,
|
||||
s->smb_dir,
|
||||
exported_dir,
|
||||
passwd->pw_name
|
||||
);
|
||||
|
14
net/tap.c
14
net/tap.c
@@ -367,11 +367,8 @@ static int launch_script(const char *setup_script, const char *ifname, int fd)
|
||||
if (pid == 0) {
|
||||
int open_max = sysconf(_SC_OPEN_MAX), i;
|
||||
|
||||
for (i = 0; i < open_max; i++) {
|
||||
if (i != STDIN_FILENO &&
|
||||
i != STDOUT_FILENO &&
|
||||
i != STDERR_FILENO &&
|
||||
i != fd) {
|
||||
for (i = 3; i < open_max; i++) {
|
||||
if (i != fd) {
|
||||
close(i);
|
||||
}
|
||||
}
|
||||
@@ -452,11 +449,8 @@ static int net_bridge_run_helper(const char *helper, const char *bridge)
|
||||
char br_buf[6+IFNAMSIZ] = {0};
|
||||
char helper_cmd[PATH_MAX + sizeof(fd_buf) + sizeof(br_buf) + 15];
|
||||
|
||||
for (i = 0; i < open_max; i++) {
|
||||
if (i != STDIN_FILENO &&
|
||||
i != STDOUT_FILENO &&
|
||||
i != STDERR_FILENO &&
|
||||
i != sv[1]) {
|
||||
for (i = 3; i < open_max; i++) {
|
||||
if (i != sv[1]) {
|
||||
close(i);
|
||||
}
|
||||
}
|
||||
|
1010
pc-bios/qemu_logo.svg
Normal file
1010
pc-bios/qemu_logo.svg
Normal file
File diff suppressed because it is too large
Load Diff
After Width: | Height: | Size: 32 KiB |
@@ -37,8 +37,8 @@ install: $(OBJS)
|
||||
$(call quiet-command, msgfmt -o $@ $<, " GEN $@")
|
||||
|
||||
$(PO_PATH)/messages.po: $(SRC_PATH)/ui/gtk.c
|
||||
$(call quiet-command, cd $(SRC_PATH) && \
|
||||
(xgettext -o - --from-code=UTF-8 --foreign-user \
|
||||
$(call quiet-command, ( cd $(SRC_PATH) && \
|
||||
xgettext -o - --from-code=UTF-8 --foreign-user \
|
||||
--package-name=QEMU --package-version=$(VERSION) \
|
||||
--msgid-bugs-address=qemu-devel@nongnu.org -k_ -C ui/gtk.c | \
|
||||
sed -e s/CHARSET/UTF-8/) >$@, " GEN $@")
|
||||
|
@@ -10,7 +10,7 @@ msgstr ""
|
||||
"PO-Revision-Date: 2012-02-28 16:00+0100\n"
|
||||
"Last-Translator: Kevin Wolf <kwolf@redhat.com>\n"
|
||||
"Language-Team: Deutsch <de@li.org>\n"
|
||||
"Language: \n"
|
||||
"Language: de\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
"Content-Type: text/plain; charset=UTF-8\n"
|
||||
"Content-Transfer-Encoding: 8bit\n"
|
||||
|
@@ -10,7 +10,7 @@ msgstr ""
|
||||
"PO-Revision-Date: 2013-03-31 19:39+0200\n"
|
||||
"Last-Translator: Aurelien Jarno <aurelien@aurel32.net>\n"
|
||||
"Language-Team: French <FR@li.org>\n"
|
||||
"Language: \n"
|
||||
"Language: fr\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
"Content-Type: text/plain; charset=UTF-8\n"
|
||||
"Content-Transfer-Encoding: 8bit\n"
|
||||
|
2
po/hu.po
2
po/hu.po
@@ -10,7 +10,7 @@ msgstr ""
|
||||
"PO-Revision-Date: 2013-05-06 20:42+0200\n"
|
||||
"Last-Translator: Ákos Kovács <akoskovacs@gmx.com>\n"
|
||||
"Language-Team: Hungarian <hu@li.org>\n"
|
||||
"Language: \n"
|
||||
"Language: hu\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
"Content-Type: text/plain; charset=UTF-8\n"
|
||||
"Content-Transfer-Encoding: 8bit\n"
|
||||
|
2
po/it.po
2
po/it.po
@@ -10,7 +10,7 @@ msgstr ""
|
||||
"PO-Revision-Date: 2012-02-27 08:23+0100\n"
|
||||
"Last-Translator: Paolo Bonzini <pbonzini@redhat.com>\n"
|
||||
"Language-Team: Italian <it@li.org>\n"
|
||||
"Language: \n"
|
||||
"Language: it\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
"Content-Type: text/plain; charset=UTF-8\n"
|
||||
"Content-Transfer-Encoding: 8bit\n"
|
||||
|
2
po/tr.po
2
po/tr.po
@@ -10,7 +10,7 @@ msgstr ""
|
||||
"PO-Revision-Date: 2013-04-22 18:35+0300\n"
|
||||
"Last-Translator: Ozan Çağlayan <ozancag@gmail.com>\n"
|
||||
"Language-Team: Türkçe <>\n"
|
||||
"Language: \n"
|
||||
"Language: tr\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
"Content-Type: text/plain; charset=UTF-8\n"
|
||||
"Content-Transfer-Encoding: 8bit\n"
|
||||
|
@@ -4285,10 +4285,13 @@
|
||||
#
|
||||
# Drivers that are supported in block device operations.
|
||||
#
|
||||
# @host_device, @host_cdrom, @host_floppy: Since 2.1
|
||||
#
|
||||
# Since: 2.0
|
||||
##
|
||||
{ 'enum': 'BlockdevDriver',
|
||||
'data': [ 'file', 'http', 'https', 'ftp', 'ftps', 'tftp', 'vvfat', 'blkdebug',
|
||||
'data': [ 'file', 'host_device', 'host_cdrom', 'host_floppy',
|
||||
'http', 'https', 'ftp', 'ftps', 'tftp', 'vvfat', 'blkdebug',
|
||||
'blkverify', 'bochs', 'cloop', 'cow', 'dmg', 'parallels', 'qcow',
|
||||
'qcow2', 'qed', 'raw', 'vdi', 'vhdx', 'vmdk', 'vpc', 'quorum' ] }
|
||||
|
||||
@@ -4555,6 +4558,9 @@
|
||||
'discriminator': 'driver',
|
||||
'data': {
|
||||
'file': 'BlockdevOptionsFile',
|
||||
'host_device':'BlockdevOptionsFile',
|
||||
'host_cdrom': 'BlockdevOptionsFile',
|
||||
'host_floppy':'BlockdevOptionsFile',
|
||||
'http': 'BlockdevOptionsFile',
|
||||
'https': 'BlockdevOptionsFile',
|
||||
'ftp': 'BlockdevOptionsFile',
|
||||
|
@@ -80,7 +80,8 @@ static QObject *do_qmp_dispatch(QObject *request, Error **errp)
|
||||
return NULL;
|
||||
}
|
||||
if (!cmd->enabled) {
|
||||
error_set(errp, QERR_COMMAND_DISABLED, command);
|
||||
error_setg(errp, "The command %s has been disabled for this instance",
|
||||
command);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
@@ -71,7 +71,7 @@ static void qmp_input_push(QmpInputVisitor *qiv, QObject *obj, Error **errp)
|
||||
GHashTable *h;
|
||||
|
||||
if (qiv->nb_stack >= QIV_STACK_SIZE) {
|
||||
error_set(errp, QERR_BUFFER_OVERRUN);
|
||||
error_setg(errp, "An internal buffer overran");
|
||||
return;
|
||||
}
|
||||
|
||||
|
@@ -422,12 +422,14 @@ static BusState *qbus_find(const char *path)
|
||||
* one child bus accept it nevertheless */
|
||||
switch (dev->num_child_bus) {
|
||||
case 0:
|
||||
qerror_report(QERR_DEVICE_NO_BUS, elem);
|
||||
qerror_report(ERROR_CLASS_GENERIC_ERROR,
|
||||
"Device '%s' has no child bus", elem);
|
||||
return NULL;
|
||||
case 1:
|
||||
return QLIST_FIRST(&dev->child_bus);
|
||||
default:
|
||||
qerror_report(QERR_DEVICE_MULTIPLE_BUSSES, elem);
|
||||
qerror_report(ERROR_CLASS_GENERIC_ERROR,
|
||||
"Device '%s' has multiple child busses", elem);
|
||||
if (!monitor_cur_is_qmp()) {
|
||||
qbus_list_bus(dev);
|
||||
}
|
||||
@@ -505,14 +507,16 @@ DeviceState *qdev_device_add(QemuOpts *opts)
|
||||
return NULL;
|
||||
}
|
||||
if (!object_dynamic_cast(OBJECT(bus), dc->bus_type)) {
|
||||
qerror_report(QERR_BAD_BUS_FOR_DEVICE,
|
||||
qerror_report(ERROR_CLASS_GENERIC_ERROR,
|
||||
"Device '%s' can't go on a %s bus",
|
||||
driver, object_get_typename(OBJECT(bus)));
|
||||
return NULL;
|
||||
}
|
||||
} else if (dc->bus_type != NULL) {
|
||||
bus = qbus_find_recursive(sysbus_get_default(), NULL, dc->bus_type);
|
||||
if (!bus) {
|
||||
qerror_report(QERR_NO_BUS_FOR_DEVICE,
|
||||
qerror_report(ERROR_CLASS_GENERIC_ERROR,
|
||||
"No '%s' bus found for device '%s'",
|
||||
dc->bus_type, driver);
|
||||
return NULL;
|
||||
}
|
||||
|
@@ -823,7 +823,7 @@ In this case, the block device must be exported using qemu-nbd:
|
||||
qemu-nbd --socket=/tmp/my_socket my_disk.qcow2
|
||||
@end example
|
||||
|
||||
The use of qemu-nbd allows to share a disk between several guests:
|
||||
The use of qemu-nbd allows sharing of a disk between several guests:
|
||||
@example
|
||||
qemu-nbd --socket=/tmp/my_socket --share=2 my_disk.qcow2
|
||||
@end example
|
||||
|
128
qemu-img.c
128
qemu-img.c
@@ -57,8 +57,22 @@ static void format_print(void *opaque, const char *name)
|
||||
printf(" %s", name);
|
||||
}
|
||||
|
||||
static void QEMU_NORETURN GCC_FMT_ATTR(1, 2) error_exit(const char *fmt, ...)
|
||||
{
|
||||
va_list ap;
|
||||
|
||||
error_printf("qemu-img: ");
|
||||
|
||||
va_start(ap, fmt);
|
||||
error_vprintf(fmt, ap);
|
||||
va_end(ap);
|
||||
|
||||
error_printf("\nTry 'qemu-img --help' for more information\n");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
/* Please keep in synch with qemu-img.texi */
|
||||
static void help(void)
|
||||
static void QEMU_NORETURN help(void)
|
||||
{
|
||||
const char *help_msg =
|
||||
"qemu-img version " QEMU_VERSION ", Copyright (c) 2004-2008 Fabrice Bellard\n"
|
||||
@@ -129,7 +143,7 @@ static void help(void)
|
||||
printf("%s\nSupported formats:", help_msg);
|
||||
bdrv_iterate_format(format_print, NULL);
|
||||
printf("\n");
|
||||
exit(1);
|
||||
exit(EXIT_SUCCESS);
|
||||
}
|
||||
|
||||
static int GCC_FMT_ATTR(2, 3) qprintf(bool quiet, const char *fmt, ...)
|
||||
@@ -262,7 +276,8 @@ static int print_block_option_help(const char *filename, const char *fmt)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static BlockDriverState *bdrv_new_open(const char *filename,
|
||||
static BlockDriverState *bdrv_new_open(const char *id,
|
||||
const char *filename,
|
||||
const char *fmt,
|
||||
int flags,
|
||||
bool require_io,
|
||||
@@ -274,7 +289,7 @@ static BlockDriverState *bdrv_new_open(const char *filename,
|
||||
Error *local_err = NULL;
|
||||
int ret;
|
||||
|
||||
bs = bdrv_new("image");
|
||||
bs = bdrv_new(id, &error_abort);
|
||||
|
||||
if (fmt) {
|
||||
drv = bdrv_find_format(fmt);
|
||||
@@ -398,7 +413,7 @@ static int img_create(int argc, char **argv)
|
||||
}
|
||||
|
||||
if (optind >= argc) {
|
||||
help();
|
||||
error_exit("Expecting image file name");
|
||||
}
|
||||
optind++;
|
||||
|
||||
@@ -421,7 +436,7 @@ static int img_create(int argc, char **argv)
|
||||
img_size = (uint64_t)sval;
|
||||
}
|
||||
if (optind != argc) {
|
||||
help();
|
||||
error_exit("Unexpected argument: %s", argv[optind]);
|
||||
}
|
||||
|
||||
bdrv_img_create(filename, fmt, base_filename, base_fmt,
|
||||
@@ -442,12 +457,12 @@ fail:
|
||||
|
||||
static void dump_json_image_check(ImageCheck *check, bool quiet)
|
||||
{
|
||||
Error *errp = NULL;
|
||||
Error *local_err = NULL;
|
||||
QString *str;
|
||||
QmpOutputVisitor *ov = qmp_output_visitor_new();
|
||||
QObject *obj;
|
||||
visit_type_ImageCheck(qmp_output_get_visitor(ov),
|
||||
&check, NULL, &errp);
|
||||
&check, NULL, &local_err);
|
||||
obj = qmp_output_get_qobject(ov);
|
||||
str = qobject_to_json_pretty(obj);
|
||||
assert(str != NULL);
|
||||
@@ -590,7 +605,8 @@ static int img_check(int argc, char **argv)
|
||||
} else if (!strcmp(optarg, "all")) {
|
||||
fix = BDRV_FIX_LEAKS | BDRV_FIX_ERRORS;
|
||||
} else {
|
||||
help();
|
||||
error_exit("Unknown option value for -r "
|
||||
"(expecting 'leaks' or 'all'): %s", optarg);
|
||||
}
|
||||
break;
|
||||
case OPTION_OUTPUT:
|
||||
@@ -602,7 +618,7 @@ static int img_check(int argc, char **argv)
|
||||
}
|
||||
}
|
||||
if (optind != argc - 1) {
|
||||
help();
|
||||
error_exit("Expecting one image file name");
|
||||
}
|
||||
filename = argv[optind++];
|
||||
|
||||
@@ -615,7 +631,7 @@ static int img_check(int argc, char **argv)
|
||||
return 1;
|
||||
}
|
||||
|
||||
bs = bdrv_new_open(filename, fmt, flags, true, quiet);
|
||||
bs = bdrv_new_open("image", filename, fmt, flags, true, quiet);
|
||||
if (!bs) {
|
||||
return 1;
|
||||
}
|
||||
@@ -713,7 +729,7 @@ static int img_commit(int argc, char **argv)
|
||||
}
|
||||
}
|
||||
if (optind != argc - 1) {
|
||||
help();
|
||||
error_exit("Expecting one image file name");
|
||||
}
|
||||
filename = argv[optind++];
|
||||
|
||||
@@ -724,7 +740,7 @@ static int img_commit(int argc, char **argv)
|
||||
return -1;
|
||||
}
|
||||
|
||||
bs = bdrv_new_open(filename, fmt, flags, true, quiet);
|
||||
bs = bdrv_new_open("image", filename, fmt, flags, true, quiet);
|
||||
if (!bs) {
|
||||
return 1;
|
||||
}
|
||||
@@ -959,7 +975,7 @@ static int img_compare(int argc, char **argv)
|
||||
|
||||
|
||||
if (optind != argc - 2) {
|
||||
help();
|
||||
error_exit("Expecting two image file names");
|
||||
}
|
||||
filename1 = argv[optind++];
|
||||
filename2 = argv[optind++];
|
||||
@@ -967,14 +983,14 @@ static int img_compare(int argc, char **argv)
|
||||
/* Initialize before goto out */
|
||||
qemu_progress_init(progress, 2.0);
|
||||
|
||||
bs1 = bdrv_new_open(filename1, fmt1, BDRV_O_FLAGS, true, quiet);
|
||||
bs1 = bdrv_new_open("image 1", filename1, fmt1, BDRV_O_FLAGS, true, quiet);
|
||||
if (!bs1) {
|
||||
error_report("Can't open file %s", filename1);
|
||||
ret = 2;
|
||||
goto out3;
|
||||
}
|
||||
|
||||
bs2 = bdrv_new_open(filename2, fmt2, BDRV_O_FLAGS, true, quiet);
|
||||
bs2 = bdrv_new_open("image 2", filename2, fmt2, BDRV_O_FLAGS, true, quiet);
|
||||
if (!bs2) {
|
||||
error_report("Can't open file %s", filename2);
|
||||
ret = 2;
|
||||
@@ -1275,7 +1291,7 @@ static int img_convert(int argc, char **argv)
|
||||
}
|
||||
|
||||
if (bs_n < 1) {
|
||||
help();
|
||||
error_exit("Must specify image file name");
|
||||
}
|
||||
|
||||
|
||||
@@ -1292,8 +1308,11 @@ static int img_convert(int argc, char **argv)
|
||||
|
||||
total_sectors = 0;
|
||||
for (bs_i = 0; bs_i < bs_n; bs_i++) {
|
||||
bs[bs_i] = bdrv_new_open(argv[optind + bs_i], fmt, BDRV_O_FLAGS, true,
|
||||
quiet);
|
||||
char *id = bs_n > 1 ? g_strdup_printf("source %d", bs_i)
|
||||
: g_strdup("source");
|
||||
bs[bs_i] = bdrv_new_open(id, argv[optind + bs_i], fmt, BDRV_O_FLAGS,
|
||||
true, quiet);
|
||||
g_free(id);
|
||||
if (!bs[bs_i]) {
|
||||
error_report("Could not open '%s'", argv[optind + bs_i]);
|
||||
ret = -1;
|
||||
@@ -1416,7 +1435,7 @@ static int img_convert(int argc, char **argv)
|
||||
return -1;
|
||||
}
|
||||
|
||||
out_bs = bdrv_new_open(out_filename, out_fmt, flags, true, quiet);
|
||||
out_bs = bdrv_new_open("target", out_filename, out_fmt, flags, true, quiet);
|
||||
if (!out_bs) {
|
||||
ret = -1;
|
||||
goto out;
|
||||
@@ -1712,12 +1731,12 @@ static void dump_snapshots(BlockDriverState *bs)
|
||||
|
||||
static void dump_json_image_info_list(ImageInfoList *list)
|
||||
{
|
||||
Error *errp = NULL;
|
||||
Error *local_err = NULL;
|
||||
QString *str;
|
||||
QmpOutputVisitor *ov = qmp_output_visitor_new();
|
||||
QObject *obj;
|
||||
visit_type_ImageInfoList(qmp_output_get_visitor(ov),
|
||||
&list, NULL, &errp);
|
||||
&list, NULL, &local_err);
|
||||
obj = qmp_output_get_qobject(ov);
|
||||
str = qobject_to_json_pretty(obj);
|
||||
assert(str != NULL);
|
||||
@@ -1729,12 +1748,12 @@ static void dump_json_image_info_list(ImageInfoList *list)
|
||||
|
||||
static void dump_json_image_info(ImageInfo *info)
|
||||
{
|
||||
Error *errp = NULL;
|
||||
Error *local_err = NULL;
|
||||
QString *str;
|
||||
QmpOutputVisitor *ov = qmp_output_visitor_new();
|
||||
QObject *obj;
|
||||
visit_type_ImageInfo(qmp_output_get_visitor(ov),
|
||||
&info, NULL, &errp);
|
||||
&info, NULL, &local_err);
|
||||
obj = qmp_output_get_qobject(ov);
|
||||
str = qobject_to_json_pretty(obj);
|
||||
assert(str != NULL);
|
||||
@@ -1799,8 +1818,8 @@ static ImageInfoList *collect_image_info_list(const char *filename,
|
||||
}
|
||||
g_hash_table_insert(filenames, (gpointer)filename, NULL);
|
||||
|
||||
bs = bdrv_new_open(filename, fmt, BDRV_O_FLAGS | BDRV_O_NO_BACKING,
|
||||
false, false);
|
||||
bs = bdrv_new_open("image", filename, fmt,
|
||||
BDRV_O_FLAGS | BDRV_O_NO_BACKING, false, false);
|
||||
if (!bs) {
|
||||
goto err;
|
||||
}
|
||||
@@ -1882,7 +1901,7 @@ static int img_info(int argc, char **argv)
|
||||
}
|
||||
}
|
||||
if (optind != argc - 1) {
|
||||
help();
|
||||
error_exit("Expecting one image file name");
|
||||
}
|
||||
filename = argv[optind++];
|
||||
|
||||
@@ -2046,10 +2065,10 @@ static int img_map(int argc, char **argv)
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (optind >= argc) {
|
||||
help();
|
||||
if (optind != argc - 1) {
|
||||
error_exit("Expecting one image file name");
|
||||
}
|
||||
filename = argv[optind++];
|
||||
filename = argv[optind];
|
||||
|
||||
if (output && !strcmp(output, "json")) {
|
||||
output_format = OFORMAT_JSON;
|
||||
@@ -2060,7 +2079,7 @@ static int img_map(int argc, char **argv)
|
||||
return 1;
|
||||
}
|
||||
|
||||
bs = bdrv_new_open(filename, fmt, BDRV_O_FLAGS, true, false);
|
||||
bs = bdrv_new_open("image", filename, fmt, BDRV_O_FLAGS, true, false);
|
||||
if (!bs) {
|
||||
return 1;
|
||||
}
|
||||
@@ -2138,7 +2157,7 @@ static int img_snapshot(int argc, char **argv)
|
||||
return 0;
|
||||
case 'l':
|
||||
if (action) {
|
||||
help();
|
||||
error_exit("Cannot mix '-l', '-a', '-c', '-d'");
|
||||
return 0;
|
||||
}
|
||||
action = SNAPSHOT_LIST;
|
||||
@@ -2146,7 +2165,7 @@ static int img_snapshot(int argc, char **argv)
|
||||
break;
|
||||
case 'a':
|
||||
if (action) {
|
||||
help();
|
||||
error_exit("Cannot mix '-l', '-a', '-c', '-d'");
|
||||
return 0;
|
||||
}
|
||||
action = SNAPSHOT_APPLY;
|
||||
@@ -2154,7 +2173,7 @@ static int img_snapshot(int argc, char **argv)
|
||||
break;
|
||||
case 'c':
|
||||
if (action) {
|
||||
help();
|
||||
error_exit("Cannot mix '-l', '-a', '-c', '-d'");
|
||||
return 0;
|
||||
}
|
||||
action = SNAPSHOT_CREATE;
|
||||
@@ -2162,7 +2181,7 @@ static int img_snapshot(int argc, char **argv)
|
||||
break;
|
||||
case 'd':
|
||||
if (action) {
|
||||
help();
|
||||
error_exit("Cannot mix '-l', '-a', '-c', '-d'");
|
||||
return 0;
|
||||
}
|
||||
action = SNAPSHOT_DELETE;
|
||||
@@ -2175,12 +2194,12 @@ static int img_snapshot(int argc, char **argv)
|
||||
}
|
||||
|
||||
if (optind != argc - 1) {
|
||||
help();
|
||||
error_exit("Expecting one image file name");
|
||||
}
|
||||
filename = argv[optind++];
|
||||
|
||||
/* Open the image */
|
||||
bs = bdrv_new_open(filename, NULL, bdrv_oflags, true, quiet);
|
||||
bs = bdrv_new_open("image", filename, NULL, bdrv_oflags, true, quiet);
|
||||
if (!bs) {
|
||||
return 1;
|
||||
}
|
||||
@@ -2288,8 +2307,11 @@ static int img_rebase(int argc, char **argv)
|
||||
progress = 0;
|
||||
}
|
||||
|
||||
if ((optind != argc - 1) || (!unsafe && !out_baseimg)) {
|
||||
help();
|
||||
if (optind != argc - 1) {
|
||||
error_exit("Expecting one image file name");
|
||||
}
|
||||
if (!unsafe && !out_baseimg) {
|
||||
error_exit("Must specify backing file (-b) or use unsafe mode (-u)");
|
||||
}
|
||||
filename = argv[optind++];
|
||||
|
||||
@@ -2309,7 +2331,7 @@ static int img_rebase(int argc, char **argv)
|
||||
* Ignore the old backing file for unsafe rebase in case we want to correct
|
||||
* the reference to a renamed or moved backing file.
|
||||
*/
|
||||
bs = bdrv_new_open(filename, fmt, flags, true, quiet);
|
||||
bs = bdrv_new_open("image", filename, fmt, flags, true, quiet);
|
||||
if (!bs) {
|
||||
return 1;
|
||||
}
|
||||
@@ -2344,7 +2366,7 @@ static int img_rebase(int argc, char **argv)
|
||||
} else {
|
||||
char backing_name[1024];
|
||||
|
||||
bs_old_backing = bdrv_new("old_backing");
|
||||
bs_old_backing = bdrv_new("old_backing", &error_abort);
|
||||
bdrv_get_backing_filename(bs, backing_name, sizeof(backing_name));
|
||||
ret = bdrv_open(&bs_old_backing, backing_name, NULL, NULL, BDRV_O_FLAGS,
|
||||
old_backing_drv, &local_err);
|
||||
@@ -2355,7 +2377,7 @@ static int img_rebase(int argc, char **argv)
|
||||
goto out;
|
||||
}
|
||||
if (out_baseimg[0]) {
|
||||
bs_new_backing = bdrv_new("new_backing");
|
||||
bs_new_backing = bdrv_new("new_backing", &error_abort);
|
||||
ret = bdrv_open(&bs_new_backing, out_baseimg, NULL, NULL,
|
||||
BDRV_O_FLAGS, new_backing_drv, &local_err);
|
||||
if (ret) {
|
||||
@@ -2549,7 +2571,7 @@ static int img_resize(int argc, char **argv)
|
||||
/* Remove size from argv manually so that negative numbers are not treated
|
||||
* as options by getopt. */
|
||||
if (argc < 3) {
|
||||
help();
|
||||
error_exit("Not enough arguments");
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -2576,7 +2598,7 @@ static int img_resize(int argc, char **argv)
|
||||
}
|
||||
}
|
||||
if (optind != argc - 1) {
|
||||
help();
|
||||
error_exit("Expecting one image file name");
|
||||
}
|
||||
filename = argv[optind++];
|
||||
|
||||
@@ -2606,7 +2628,8 @@ static int img_resize(int argc, char **argv)
|
||||
n = qemu_opt_get_size(param, BLOCK_OPT_SIZE, 0);
|
||||
qemu_opts_del(param);
|
||||
|
||||
bs = bdrv_new_open(filename, fmt, BDRV_O_FLAGS | BDRV_O_RDWR, true, quiet);
|
||||
bs = bdrv_new_open("image", filename, fmt, BDRV_O_FLAGS | BDRV_O_RDWR,
|
||||
true, quiet);
|
||||
if (!bs) {
|
||||
ret = -1;
|
||||
goto out;
|
||||
@@ -2692,7 +2715,7 @@ static int img_amend(int argc, char **argv)
|
||||
}
|
||||
|
||||
if (!options) {
|
||||
help();
|
||||
error_exit("Must specify options (-o)");
|
||||
}
|
||||
|
||||
filename = (optind == argc - 1) ? argv[argc - 1] : NULL;
|
||||
@@ -2704,10 +2727,11 @@ static int img_amend(int argc, char **argv)
|
||||
}
|
||||
|
||||
if (optind != argc - 1) {
|
||||
help();
|
||||
error_exit("Expecting one image file name");
|
||||
}
|
||||
|
||||
bs = bdrv_new_open(filename, fmt, BDRV_O_FLAGS | BDRV_O_RDWR, true, quiet);
|
||||
bs = bdrv_new_open("image", filename, fmt,
|
||||
BDRV_O_FLAGS | BDRV_O_RDWR, true, quiet);
|
||||
if (!bs) {
|
||||
error_report("Could not open image '%s'", filename);
|
||||
ret = -1;
|
||||
@@ -2775,8 +2799,9 @@ int main(int argc, char **argv)
|
||||
|
||||
qemu_init_main_loop();
|
||||
bdrv_init();
|
||||
if (argc < 2)
|
||||
help();
|
||||
if (argc < 2) {
|
||||
error_exit("Not enough arguments");
|
||||
}
|
||||
cmdname = argv[1];
|
||||
argc--; argv++;
|
||||
|
||||
@@ -2788,6 +2813,5 @@ int main(int argc, char **argv)
|
||||
}
|
||||
|
||||
/* not found */
|
||||
help();
|
||||
return 0;
|
||||
error_exit("Command not found: %s", cmdname);
|
||||
}
|
||||
|
@@ -67,7 +67,7 @@ static int openfile(char *name, int flags, int growable, QDict *opts)
|
||||
return 1;
|
||||
}
|
||||
} else {
|
||||
qemuio_bs = bdrv_new("hda");
|
||||
qemuio_bs = bdrv_new("hda", &error_abort);
|
||||
|
||||
if (bdrv_open(&qemuio_bs, name, NULL, opts, flags, NULL, &local_err)
|
||||
< 0)
|
||||
|
@@ -657,7 +657,8 @@ int main(int argc, char **argv)
|
||||
drv = NULL;
|
||||
}
|
||||
|
||||
bs = bdrv_new("hda");
|
||||
bs = bdrv_new("hda", &error_abort);
|
||||
|
||||
srcpath = argv[optind];
|
||||
ret = bdrv_open(&bs, srcpath, NULL, NULL, flags, drv, &local_err);
|
||||
if (ret < 0) {
|
||||
|
@@ -210,10 +210,13 @@ use is discouraged as it may be removed from future versions.
|
||||
ETEXI
|
||||
|
||||
DEF("m", HAS_ARG, QEMU_OPTION_m,
|
||||
"-m megs set virtual RAM size to megs MB [default="
|
||||
stringify(DEFAULT_RAM_SIZE) "]\n", QEMU_ARCH_ALL)
|
||||
"-m [size=]megs\n"
|
||||
" configure guest RAM\n"
|
||||
" size: initial amount of guest memory (default: "
|
||||
stringify(DEFAULT_RAM_SIZE) "MiB)\n",
|
||||
QEMU_ARCH_ALL)
|
||||
STEXI
|
||||
@item -m @var{megs}
|
||||
@item -m [size=]@var{megs}
|
||||
@findex -m
|
||||
Set virtual RAM size to @var{megs} megabytes. Default is 128 MiB. Optionally,
|
||||
a suffix of ``M'' or ``G'' can be used to signify a value in megabytes or
|
||||
@@ -408,7 +411,8 @@ DEF("drive", HAS_ARG, QEMU_OPTION_drive,
|
||||
"-drive [file=file][,if=type][,bus=n][,unit=m][,media=d][,index=i]\n"
|
||||
" [,cyls=c,heads=h,secs=s[,trans=t]][,snapshot=on|off]\n"
|
||||
" [,cache=writethrough|writeback|none|directsync|unsafe][,format=f]\n"
|
||||
" [,serial=s][,addr=A][,id=name][,aio=threads|native]\n"
|
||||
" [,serial=s][,addr=A][,rerror=ignore|stop|report]\n"
|
||||
" [,werror=ignore|stop|report|enospc][,id=name][,aio=threads|native]\n"
|
||||
" [,readonly=on|off][,copy-on-read=on|off]\n"
|
||||
" [[,bps=b]|[[,bps_rd=r][,bps_wr=w]]]\n"
|
||||
" [[,iops=i]|[[,iops_rd=r][,iops_wr=w]]]\n"
|
||||
@@ -444,7 +448,8 @@ This option defines the type of the media: disk or cdrom.
|
||||
@item cyls=@var{c},heads=@var{h},secs=@var{s}[,trans=@var{t}]
|
||||
These options have the same definition as they have in @option{-hdachs}.
|
||||
@item snapshot=@var{snapshot}
|
||||
@var{snapshot} is "on" or "off" and allows to enable snapshot for given drive (see @option{-snapshot}).
|
||||
@var{snapshot} is "on" or "off" and controls snapshot mode for the given drive
|
||||
(see @option{-snapshot}).
|
||||
@item cache=@var{cache}
|
||||
@var{cache} is "none", "writeback", "unsafe", "directsync" or "writethrough" and controls how the host cache is used to access block data.
|
||||
@item aio=@var{aio}
|
||||
@@ -1242,7 +1247,7 @@ Disable adaptive encodings. Adaptive encodings are enabled by default.
|
||||
An adaptive encoding will try to detect frequently updated screen regions,
|
||||
and send updates in these regions using a lossy encoding (like JPEG).
|
||||
This can be really helpful to save bandwidth when playing videos. Disabling
|
||||
adaptive encodings allows to restore the original static behavior of encodings
|
||||
adaptive encodings restores the original static behavior of encodings
|
||||
like Tight.
|
||||
|
||||
@item share=[allow-exclusive|force-shared|ignore]
|
||||
@@ -2805,7 +2810,7 @@ UTC or local time, respectively. @code{localtime} is required for correct date i
|
||||
MS-DOS or Windows. To start at a specific point in time, provide @var{date} in the
|
||||
format @code{2006-06-17T16:01:21} or @code{2006-06-17}. The default base is UTC.
|
||||
|
||||
By default the RTC is driven by the host system time. This allows to use the
|
||||
By default the RTC is driven by the host system time. This allows using of the
|
||||
RTC as accurate reference clock inside the guest, specifically if the host
|
||||
time is smoothly following an accurate external reference clock, e.g. via NTP.
|
||||
If you want to isolate the guest time from the host, you can set @option{clock}
|
||||
|
@@ -143,6 +143,7 @@ static const struct QemuSeccompSyscall seccomp_whitelist[] = {
|
||||
{ SCMP_SYS(getsockname), 242 },
|
||||
{ SCMP_SYS(getpeername), 242 },
|
||||
{ SCMP_SYS(accept4), 242 },
|
||||
{ SCMP_SYS(timerfd_settime), 242 },
|
||||
{ SCMP_SYS(newfstatat), 241 },
|
||||
{ SCMP_SYS(shutdown), 241 },
|
||||
{ SCMP_SYS(getsockopt), 241 },
|
||||
@@ -225,7 +226,11 @@ static const struct QemuSeccompSyscall seccomp_whitelist[] = {
|
||||
{ SCMP_SYS(fchmod), 240 },
|
||||
{ SCMP_SYS(shmget), 240 },
|
||||
{ SCMP_SYS(shmat), 240 },
|
||||
{ SCMP_SYS(shmdt), 240 }
|
||||
{ SCMP_SYS(shmdt), 240 },
|
||||
{ SCMP_SYS(timerfd_create), 240 },
|
||||
{ SCMP_SYS(shmctl), 240 },
|
||||
{ SCMP_SYS(mlock), 240 },
|
||||
{ SCMP_SYS(munlock), 240 }
|
||||
};
|
||||
|
||||
int seccomp_start(void)
|
||||
|
@@ -171,7 +171,7 @@ void qmp_guest_set_time(bool has_time, int64_t time_ns, Error **errp)
|
||||
/* Now, if user has passed a time to set and the system time is set, we
|
||||
* just need to synchronize the hardware clock. However, if no time was
|
||||
* passed, user is requesting the opposite: set the system time from the
|
||||
* hardware clock. */
|
||||
* hardware clock (RTC). */
|
||||
pid = fork();
|
||||
if (pid == 0) {
|
||||
setsid();
|
||||
|
@@ -96,8 +96,8 @@
|
||||
##
|
||||
# @guest-get-time:
|
||||
#
|
||||
# Get the information about guest time relative to the Epoch
|
||||
# of 1970-01-01 in UTC.
|
||||
# Get the information about guest's System Time relative to
|
||||
# the Epoch of 1970-01-01 in UTC.
|
||||
#
|
||||
# Returns: Time in nanoseconds.
|
||||
#
|
||||
@@ -117,11 +117,11 @@
|
||||
# gap was, NTP might not be able to resynchronize the
|
||||
# guest.
|
||||
#
|
||||
# This command tries to set guest time to the given value,
|
||||
# then sets the Hardware Clock to the current System Time.
|
||||
# This will make it easier for a guest to resynchronize
|
||||
# without waiting for NTP. If no @time is specified, then
|
||||
# the time to set is read from RTC.
|
||||
# This command tries to set guest's System Time to the
|
||||
# given value, then sets the Hardware Clock (RTC) to the
|
||||
# current System Time. This will make it easier for a guest
|
||||
# to resynchronize without waiting for NTP. If no @time is
|
||||
# specified, then the time to set is read from RTC.
|
||||
#
|
||||
# @time: #optional time of nanoseconds, relative to the Epoch
|
||||
# of 1970-01-01 in UTC.
|
||||
|
23
qmp.c
23
qmp.c
@@ -166,7 +166,7 @@ void qmp_cont(Error **errp)
|
||||
Error *local_err = NULL;
|
||||
|
||||
if (runstate_needs_reset()) {
|
||||
error_set(errp, QERR_RESET_REQUIRED);
|
||||
error_setg(errp, "Resetting the Virtual Machine is required");
|
||||
return;
|
||||
} else if (runstate_check(RUN_STATE_SUSPENDED)) {
|
||||
return;
|
||||
@@ -540,14 +540,27 @@ void object_add(const char *type, const char *id, const QDict *qdict,
|
||||
Visitor *v, Error **errp)
|
||||
{
|
||||
Object *obj;
|
||||
ObjectClass *klass;
|
||||
const QDictEntry *e;
|
||||
Error *local_err = NULL;
|
||||
|
||||
if (!object_class_by_name(type)) {
|
||||
klass = object_class_by_name(type);
|
||||
if (!klass) {
|
||||
error_setg(errp, "invalid class name");
|
||||
return;
|
||||
}
|
||||
|
||||
if (!object_class_dynamic_cast(klass, TYPE_USER_CREATABLE)) {
|
||||
error_setg(errp, "object type '%s' isn't supported by object-add",
|
||||
type);
|
||||
return;
|
||||
}
|
||||
|
||||
if (object_class_is_abstract(klass)) {
|
||||
error_setg(errp, "object type '%s' is abstract", type);
|
||||
return;
|
||||
}
|
||||
|
||||
obj = object_new(type);
|
||||
if (qdict) {
|
||||
for (e = qdict_first(qdict); e; e = qdict_next(qdict, e)) {
|
||||
@@ -558,12 +571,6 @@ void object_add(const char *type, const char *id, const QDict *qdict,
|
||||
}
|
||||
}
|
||||
|
||||
if (!object_dynamic_cast(obj, TYPE_USER_CREATABLE)) {
|
||||
error_setg(&local_err, "object type '%s' isn't supported by object-add",
|
||||
type);
|
||||
goto out;
|
||||
}
|
||||
|
||||
user_creatable_complete(obj, &local_err);
|
||||
if (local_err) {
|
||||
goto out;
|
||||
|
@@ -110,7 +110,7 @@ static void GCC_FMT_ATTR(3, 4) parse_error(JSONParserContext *ctxt,
|
||||
error_free(ctxt->err);
|
||||
ctxt->err = NULL;
|
||||
}
|
||||
error_set(&ctxt->err, QERR_JSON_PARSE_ERROR, message);
|
||||
error_setg(&ctxt->err, "JSON parse error, %s", message);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@@ -768,7 +768,7 @@ ObjectProperty *object_property_find(Object *obj, const char *name,
|
||||
}
|
||||
}
|
||||
|
||||
error_set(errp, QERR_PROPERTY_NOT_FOUND, "", name);
|
||||
error_setg(errp, "Property '.%s' not found", name);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@@ -1075,7 +1075,8 @@ static Object *object_resolve_link(Object *obj, const char *name,
|
||||
target = object_resolve_path_type(path, target_type, &ambiguous);
|
||||
|
||||
if (ambiguous) {
|
||||
error_set(errp, QERR_AMBIGUOUS_PATH, path);
|
||||
error_set(errp, ERROR_CLASS_GENERIC_ERROR,
|
||||
"Path '%s' does not uniquely identify an object", path);
|
||||
} else if (!target) {
|
||||
target = object_resolve_path(path, &ambiguous);
|
||||
if (target || ambiguous) {
|
||||
|
3
savevm.c
3
savevm.c
@@ -453,7 +453,8 @@ bool qemu_savevm_state_blocked(Error **errp)
|
||||
|
||||
QTAILQ_FOREACH(se, &savevm_handlers, entry) {
|
||||
if (se->no_migrate) {
|
||||
error_set(errp, QERR_MIGRATION_NOT_SUPPORTED, se->idstr);
|
||||
error_setg(errp, "State blocked by non-migratable device '%s'",
|
||||
se->idstr);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
183
scripts/coverity-model.c
Normal file
183
scripts/coverity-model.c
Normal file
@@ -0,0 +1,183 @@
|
||||
/* Coverity Scan model
|
||||
*
|
||||
* Copyright (C) 2014 Red Hat, Inc.
|
||||
*
|
||||
* Authors:
|
||||
* Markus Armbruster <armbru@redhat.com>
|
||||
* Paolo Bonzini <pbonzini@redhat.com>
|
||||
*
|
||||
* This work is licensed under the terms of the GNU GPL, version 2 or, at your
|
||||
* option, any later version. See the COPYING file in the top-level directory.
|
||||
*/
|
||||
|
||||
|
||||
/*
|
||||
* This is the source code for our Coverity user model file. The
|
||||
* purpose of user models is to increase scanning accuracy by explaining
|
||||
* code Coverity can't see (out of tree libraries) or doesn't
|
||||
* sufficiently understand. Better accuracy means both fewer false
|
||||
* positives and more true defects. Memory leaks in particular.
|
||||
*
|
||||
* - A model file can't import any header files. Some built-in primitives are
|
||||
* available but not wchar_t, NULL etc.
|
||||
* - Modeling doesn't need full structs and typedefs. Rudimentary structs
|
||||
* and similar types are sufficient.
|
||||
* - An uninitialized local variable signifies that the variable could be
|
||||
* any value.
|
||||
*
|
||||
* The model file must be uploaded by an admin in the analysis settings of
|
||||
* http://scan.coverity.com/projects/378
|
||||
*/
|
||||
|
||||
#define NULL ((void *)0)
|
||||
|
||||
typedef unsigned char uint8_t;
|
||||
typedef char int8_t;
|
||||
typedef unsigned int uint32_t;
|
||||
typedef int int32_t;
|
||||
typedef long ssize_t;
|
||||
typedef unsigned long long uint64_t;
|
||||
typedef long long int64_t;
|
||||
typedef _Bool bool;
|
||||
|
||||
/* exec.c */
|
||||
|
||||
typedef struct AddressSpace AddressSpace;
|
||||
typedef uint64_t hwaddr;
|
||||
|
||||
static void __write(uint8_t *buf, ssize_t len)
|
||||
{
|
||||
int first, last;
|
||||
__coverity_negative_sink__(len);
|
||||
if (len == 0) return;
|
||||
buf[0] = first;
|
||||
buf[len-1] = last;
|
||||
__coverity_writeall__(buf);
|
||||
}
|
||||
|
||||
static void __read(uint8_t *buf, ssize_t len)
|
||||
{
|
||||
__coverity_negative_sink__(len);
|
||||
if (len == 0) return;
|
||||
int first = buf[0];
|
||||
int last = buf[len-1];
|
||||
}
|
||||
|
||||
bool address_space_rw(AddressSpace *as, hwaddr addr, uint8_t *buf,
|
||||
int len, bool is_write)
|
||||
{
|
||||
bool result;
|
||||
|
||||
// TODO: investigate impact of treating reads as producing
|
||||
// tainted data, with __coverity_tainted_data_argument__(buf).
|
||||
if (is_write) __write(buf, len); else __read(buf, len);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
/* Tainting */
|
||||
|
||||
typedef struct {} name2keysym_t;
|
||||
static int get_keysym(const name2keysym_t *table,
|
||||
const char *name)
|
||||
{
|
||||
int result;
|
||||
if (result > 0) {
|
||||
__coverity_tainted_string_sanitize_content__(name);
|
||||
return result;
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* glib memory allocation functions.
|
||||
*
|
||||
* Note that we ignore the fact that g_malloc of 0 bytes returns NULL,
|
||||
* and g_realloc of 0 bytes frees the pointer.
|
||||
*
|
||||
* Modeling this would result in Coverity flagging a lot of memory
|
||||
* allocations as potentially returning NULL, and asking us to check
|
||||
* whether the result of the allocation is NULL or not. However, the
|
||||
* resulting pointer should never be dereferenced anyway, and in fact
|
||||
* it is not in the vast majority of cases.
|
||||
*
|
||||
* If a dereference did happen, this would suppress a defect report
|
||||
* for an actual null pointer dereference. But it's too unlikely to
|
||||
* be worth wading through the false positives, and with some luck
|
||||
* we'll get a buffer overflow reported anyway.
|
||||
*/
|
||||
|
||||
void *malloc(size_t);
|
||||
void *calloc(size_t, size_t);
|
||||
void *realloc(void *, size_t);
|
||||
void free(void *);
|
||||
|
||||
void *
|
||||
g_malloc(size_t n_bytes)
|
||||
{
|
||||
void *mem;
|
||||
__coverity_negative_sink__(n_bytes);
|
||||
mem = malloc(n_bytes == 0 ? 1 : n_bytes);
|
||||
if (!mem) __coverity_panic__();
|
||||
return mem;
|
||||
}
|
||||
|
||||
void *
|
||||
g_malloc0(size_t n_bytes)
|
||||
{
|
||||
void *mem;
|
||||
__coverity_negative_sink__(n_bytes);
|
||||
mem = calloc(1, n_bytes == 0 ? 1 : n_bytes);
|
||||
if (!mem) __coverity_panic__();
|
||||
return mem;
|
||||
}
|
||||
|
||||
void g_free(void *mem)
|
||||
{
|
||||
free(mem);
|
||||
}
|
||||
|
||||
void *g_realloc(void * mem, size_t n_bytes)
|
||||
{
|
||||
__coverity_negative_sink__(n_bytes);
|
||||
mem = realloc(mem, n_bytes == 0 ? 1 : n_bytes);
|
||||
if (!mem) __coverity_panic__();
|
||||
return mem;
|
||||
}
|
||||
|
||||
void *g_try_malloc(size_t n_bytes)
|
||||
{
|
||||
__coverity_negative_sink__(n_bytes);
|
||||
return malloc(n_bytes == 0 ? 1 : n_bytes);
|
||||
}
|
||||
|
||||
void *g_try_malloc0(size_t n_bytes)
|
||||
{
|
||||
__coverity_negative_sink__(n_bytes);
|
||||
return calloc(1, n_bytes == 0 ? 1 : n_bytes);
|
||||
}
|
||||
|
||||
void *g_try_realloc(void *mem, size_t n_bytes)
|
||||
{
|
||||
__coverity_negative_sink__(n_bytes);
|
||||
return realloc(mem, n_bytes == 0 ? 1 : n_bytes);
|
||||
}
|
||||
|
||||
/* Other glib functions */
|
||||
|
||||
typedef struct _GIOChannel GIOChannel;
|
||||
GIOChannel *g_io_channel_unix_new(int fd)
|
||||
{
|
||||
GIOChannel *c = g_malloc0(sizeof(GIOChannel));
|
||||
__coverity_escape__(fd);
|
||||
return c;
|
||||
}
|
||||
|
||||
void g_assertion_message_expr(const char *domain,
|
||||
const char *file,
|
||||
int line,
|
||||
const char *func,
|
||||
const char *expr)
|
||||
{
|
||||
__coverity_panic__();
|
||||
}
|
13
slirp/misc.c
13
slirp/misc.c
@@ -136,7 +136,7 @@ fork_exec(struct socket *so, const char *ex, int do_pty)
|
||||
if ((s = qemu_socket(AF_INET, SOCK_STREAM, 0)) < 0 ||
|
||||
bind(s, (struct sockaddr *)&addr, addrlen) < 0 ||
|
||||
listen(s, 1) < 0) {
|
||||
lprint("Error: inet socket: %s\n", strerror(errno));
|
||||
error_report("Error: inet socket: %s", strerror(errno));
|
||||
closesocket(s);
|
||||
|
||||
return 0;
|
||||
@@ -146,7 +146,7 @@ fork_exec(struct socket *so, const char *ex, int do_pty)
|
||||
pid = fork();
|
||||
switch(pid) {
|
||||
case -1:
|
||||
lprint("Error: fork failed: %s\n", strerror(errno));
|
||||
error_report("Error: fork failed: %s", strerror(errno));
|
||||
close(s);
|
||||
return 0;
|
||||
|
||||
@@ -242,15 +242,6 @@ strdup(str)
|
||||
}
|
||||
#endif
|
||||
|
||||
void lprint(const char *format, ...)
|
||||
{
|
||||
va_list args;
|
||||
|
||||
va_start(args, format);
|
||||
monitor_vprintf(default_mon, format, args);
|
||||
va_end(args);
|
||||
}
|
||||
|
||||
void slirp_connection_info(Slirp *slirp, Monitor *mon)
|
||||
{
|
||||
const char * const tcpstates[] = {
|
||||
|
@@ -139,7 +139,7 @@ int get_dns_addr(struct in_addr *pdns_addr)
|
||||
return -1;
|
||||
|
||||
#ifdef DEBUG
|
||||
lprint("IP address of your DNS(s): ");
|
||||
fprintf(stderr, "IP address of your DNS(s): ");
|
||||
#endif
|
||||
while (fgets(buff, 512, f) != NULL) {
|
||||
if (sscanf(buff, "nameserver%*[ \t]%256s", buff2) == 1) {
|
||||
@@ -153,17 +153,17 @@ int get_dns_addr(struct in_addr *pdns_addr)
|
||||
}
|
||||
#ifdef DEBUG
|
||||
else
|
||||
lprint(", ");
|
||||
fprintf(stderr, ", ");
|
||||
#endif
|
||||
if (++found > 3) {
|
||||
#ifdef DEBUG
|
||||
lprint("(more)");
|
||||
fprintf(stderr, "(more)");
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
#ifdef DEBUG
|
||||
else
|
||||
lprint("%s", inet_ntoa(tmp_addr));
|
||||
fprintf(stderr, "%s", inet_ntoa(tmp_addr));
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
@@ -287,8 +287,6 @@ void if_start(struct ttys *);
|
||||
long gethostid(void);
|
||||
#endif
|
||||
|
||||
void lprint(const char *, ...) GCC_FMT_ATTR(1, 2);
|
||||
|
||||
#ifndef _WIN32
|
||||
#include <netdb.h>
|
||||
#endif
|
||||
|
@@ -14,7 +14,6 @@ stub-obj-y += iothread-lock.o
|
||||
stub-obj-y += migr-blocker.o
|
||||
stub-obj-y += mon-is-qmp.o
|
||||
stub-obj-y += mon-printf.o
|
||||
stub-obj-y += mon-print-filename.o
|
||||
stub-obj-y += mon-protocol-event.o
|
||||
stub-obj-y += mon-set-error.o
|
||||
stub-obj-y += pci-drive-hot-add.o
|
||||
|
@@ -4,6 +4,6 @@
|
||||
|
||||
CpuDefinitionInfoList *arch_query_cpu_definitions(Error **errp)
|
||||
{
|
||||
error_set(errp, QERR_NOT_SUPPORTED);
|
||||
error_set(errp, QERR_UNSUPPORTED);
|
||||
return NULL;
|
||||
}
|
||||
|
@@ -1,6 +0,0 @@
|
||||
#include "qemu-common.h"
|
||||
#include "monitor/monitor.h"
|
||||
|
||||
void monitor_print_filename(Monitor *mon, const char *filename)
|
||||
{
|
||||
}
|
@@ -820,3 +820,10 @@ uint64_t helper_cvtqg(CPUAlphaState *env, uint64_t a)
|
||||
fr = int64_to_float64(a, &FP_STATUS);
|
||||
return float64_to_g(fr);
|
||||
}
|
||||
|
||||
void helper_fcvtql_v_input(CPUAlphaState *env, uint64_t val)
|
||||
{
|
||||
if (val != (int32_t)val) {
|
||||
arith_excp(env, GETPC(), EXC_M_IOV, 0);
|
||||
}
|
||||
}
|
||||
|
@@ -96,6 +96,7 @@ DEF_HELPER_FLAGS_3(fp_exc_raise_s, TCG_CALL_NO_WG, void, env, i32, i32)
|
||||
|
||||
DEF_HELPER_FLAGS_2(ieee_input, TCG_CALL_NO_WG, void, env, i64)
|
||||
DEF_HELPER_FLAGS_2(ieee_input_cmp, TCG_CALL_NO_WG, void, env, i64)
|
||||
DEF_HELPER_FLAGS_2(fcvtql_v_input, TCG_CALL_NO_WG, void, env, i64)
|
||||
|
||||
#if !defined (CONFIG_USER_ONLY)
|
||||
DEF_HELPER_2(hw_ret, void, env, i64)
|
||||
|
File diff suppressed because it is too large
Load Diff
@@ -116,6 +116,7 @@ typedef struct ARMCPU {
|
||||
uint32_t reset_fpsid;
|
||||
uint32_t mvfr0;
|
||||
uint32_t mvfr1;
|
||||
uint32_t mvfr2;
|
||||
uint32_t ctr;
|
||||
uint32_t reset_sctlr;
|
||||
uint32_t id_pfr0;
|
||||
@@ -147,9 +148,12 @@ typedef struct ARMCPU {
|
||||
* in the order L1DCache, L1ICache, L2DCache, L2ICache, etc.
|
||||
*/
|
||||
uint32_t ccsidr[16];
|
||||
uint32_t reset_cbar;
|
||||
uint64_t reset_cbar;
|
||||
uint32_t reset_auxcr;
|
||||
bool reset_hivecs;
|
||||
/* DCZ blocksize, in log_2(words), ie low 4 bits of DCZID_EL0 */
|
||||
uint32_t dcz_blocksize;
|
||||
uint64_t rvbar;
|
||||
} ARMCPU;
|
||||
|
||||
#define TYPE_AARCH64_CPU "aarch64-cpu"
|
||||
@@ -196,10 +200,10 @@ void arm_gt_ptimer_cb(void *opaque);
|
||||
void arm_gt_vtimer_cb(void *opaque);
|
||||
|
||||
#ifdef TARGET_AARCH64
|
||||
void aarch64_cpu_dump_state(CPUState *cs, FILE *f,
|
||||
fprintf_function cpu_fprintf, int flags);
|
||||
int aarch64_cpu_gdb_read_register(CPUState *cpu, uint8_t *buf, int reg);
|
||||
int aarch64_cpu_gdb_write_register(CPUState *cpu, uint8_t *buf, int reg);
|
||||
|
||||
void aarch64_cpu_do_interrupt(CPUState *cs);
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
@@ -19,6 +19,7 @@
|
||||
*/
|
||||
|
||||
#include "cpu.h"
|
||||
#include "internals.h"
|
||||
#include "qemu-common.h"
|
||||
#include "hw/qdev-properties.h"
|
||||
#include "qapi/qmp/qerror.h"
|
||||
@@ -87,6 +88,7 @@ static void arm_cpu_reset(CPUState *s)
|
||||
env->vfp.xregs[ARM_VFP_FPSID] = cpu->reset_fpsid;
|
||||
env->vfp.xregs[ARM_VFP_MVFR0] = cpu->mvfr0;
|
||||
env->vfp.xregs[ARM_VFP_MVFR1] = cpu->mvfr1;
|
||||
env->vfp.xregs[ARM_VFP_MVFR2] = cpu->mvfr2;
|
||||
|
||||
if (arm_feature(env, ARM_FEATURE_IWMMXT)) {
|
||||
env->iwmmxt.cregs[ARM_IWMMXT_wCID] = 0x69051000 | 'Q';
|
||||
@@ -99,8 +101,16 @@ static void arm_cpu_reset(CPUState *s)
|
||||
env->pstate = PSTATE_MODE_EL0t;
|
||||
/* Userspace expects access to CTL_EL0 and the cache ops */
|
||||
env->cp15.c1_sys |= SCTLR_UCT | SCTLR_UCI;
|
||||
/* and to the FP/Neon instructions */
|
||||
env->cp15.c1_coproc = deposit64(env->cp15.c1_coproc, 20, 2, 3);
|
||||
#else
|
||||
env->pstate = PSTATE_MODE_EL1h;
|
||||
env->pc = cpu->rvbar;
|
||||
#endif
|
||||
} else {
|
||||
#if defined(CONFIG_USER_ONLY)
|
||||
/* Userspace expects access to cp10 and cp11 for FP/Neon */
|
||||
env->cp15.c1_coproc = deposit64(env->cp15.c1_coproc, 20, 4, 0xf);
|
||||
#endif
|
||||
}
|
||||
|
||||
@@ -252,16 +262,20 @@ static void arm_cpu_initfn(Object *obj)
|
||||
}
|
||||
|
||||
static Property arm_cpu_reset_cbar_property =
|
||||
DEFINE_PROP_UINT32("reset-cbar", ARMCPU, reset_cbar, 0);
|
||||
DEFINE_PROP_UINT64("reset-cbar", ARMCPU, reset_cbar, 0);
|
||||
|
||||
static Property arm_cpu_reset_hivecs_property =
|
||||
DEFINE_PROP_BOOL("reset-hivecs", ARMCPU, reset_hivecs, false);
|
||||
|
||||
static Property arm_cpu_rvbar_property =
|
||||
DEFINE_PROP_UINT64("rvbar", ARMCPU, rvbar, 0);
|
||||
|
||||
static void arm_cpu_post_init(Object *obj)
|
||||
{
|
||||
ARMCPU *cpu = ARM_CPU(obj);
|
||||
|
||||
if (arm_feature(&cpu->env, ARM_FEATURE_CBAR)) {
|
||||
if (arm_feature(&cpu->env, ARM_FEATURE_CBAR) ||
|
||||
arm_feature(&cpu->env, ARM_FEATURE_CBAR_RO)) {
|
||||
qdev_property_add_static(DEVICE(obj), &arm_cpu_reset_cbar_property,
|
||||
&error_abort);
|
||||
}
|
||||
@@ -270,6 +284,11 @@ static void arm_cpu_post_init(Object *obj)
|
||||
qdev_property_add_static(DEVICE(obj), &arm_cpu_reset_hivecs_property,
|
||||
&error_abort);
|
||||
}
|
||||
|
||||
if (arm_feature(&cpu->env, ARM_FEATURE_AARCH64)) {
|
||||
qdev_property_add_static(DEVICE(obj), &arm_cpu_rvbar_property,
|
||||
&error_abort);
|
||||
}
|
||||
}
|
||||
|
||||
static void arm_cpu_finalizefn(Object *obj)
|
||||
@@ -331,6 +350,9 @@ static void arm_cpu_realizefn(DeviceState *dev, Error **errp)
|
||||
set_feature(env, ARM_FEATURE_V7MP);
|
||||
set_feature(env, ARM_FEATURE_PXN);
|
||||
}
|
||||
if (arm_feature(env, ARM_FEATURE_CBAR_RO)) {
|
||||
set_feature(env, ARM_FEATURE_CBAR);
|
||||
}
|
||||
|
||||
if (cpu->reset_hivecs) {
|
||||
cpu->reset_sctlr |= (1 << 13);
|
||||
@@ -417,7 +439,7 @@ static void arm1026_initfn(Object *obj)
|
||||
ARMCPRegInfo ifar = {
|
||||
.name = "IFAR", .cp = 15, .crn = 6, .crm = 0, .opc1 = 0, .opc2 = 1,
|
||||
.access = PL1_RW,
|
||||
.fieldoffset = offsetof(CPUARMState, cp15.c6_insn),
|
||||
.fieldoffset = offsetofhigh32(CPUARMState, cp15.far_el1),
|
||||
.resetvalue = 0
|
||||
};
|
||||
define_one_arm_cp_reg(cpu, &ifar);
|
||||
@@ -722,7 +744,7 @@ static void cortex_a15_initfn(Object *obj)
|
||||
set_feature(&cpu->env, ARM_FEATURE_ARM_DIV);
|
||||
set_feature(&cpu->env, ARM_FEATURE_GENERIC_TIMER);
|
||||
set_feature(&cpu->env, ARM_FEATURE_DUMMY_C15_REGS);
|
||||
set_feature(&cpu->env, ARM_FEATURE_CBAR);
|
||||
set_feature(&cpu->env, ARM_FEATURE_CBAR_RO);
|
||||
set_feature(&cpu->env, ARM_FEATURE_LPAE);
|
||||
cpu->kvm_target = QEMU_KVM_ARM_TARGET_CORTEX_A15;
|
||||
cpu->midr = 0x412fc0f1;
|
||||
|
@@ -111,11 +111,6 @@ typedef struct ARMGenericTimer {
|
||||
#define GTIMER_VIRT 1
|
||||
#define NUM_GTIMERS 2
|
||||
|
||||
/* Scale factor for generic timers, ie number of ns per tick.
|
||||
* This gives a 62.5MHz timer.
|
||||
*/
|
||||
#define GTIMER_SCALE 16
|
||||
|
||||
typedef struct CPUARMState {
|
||||
/* Regs for current mode. */
|
||||
uint32_t regs[16];
|
||||
@@ -148,7 +143,7 @@ typedef struct CPUARMState {
|
||||
uint32_t spsr;
|
||||
|
||||
/* Banked registers. */
|
||||
uint32_t banked_spsr[6];
|
||||
uint64_t banked_spsr[6];
|
||||
uint32_t banked_r13[6];
|
||||
uint32_t banked_r14[6];
|
||||
|
||||
@@ -165,7 +160,10 @@ typedef struct CPUARMState {
|
||||
uint32_t GE; /* cpsr[19:16] */
|
||||
uint32_t thumb; /* cpsr[5]. 0 = arm mode, 1 = thumb mode. */
|
||||
uint32_t condexec_bits; /* IT bits. cpsr[15:10,26:25]. */
|
||||
uint32_t daif; /* exception masks, in the bits they are in in PSTATE */
|
||||
uint64_t daif; /* exception masks, in the bits they are in in PSTATE */
|
||||
|
||||
uint64_t elr_el1; /* AArch64 ELR_EL1 */
|
||||
uint64_t sp_el[2]; /* AArch64 banked stack pointers */
|
||||
|
||||
/* System control coprocessor (cp15) */
|
||||
struct {
|
||||
@@ -184,13 +182,13 @@ typedef struct CPUARMState {
|
||||
uint32_t c2_insn; /* MPU instruction cachable bits. */
|
||||
uint32_t c3; /* MMU domain access control register
|
||||
MPU write buffer control. */
|
||||
uint32_t c5_insn; /* Fault status registers. */
|
||||
uint32_t c5_data;
|
||||
uint32_t pmsav5_data_ap; /* PMSAv5 MPU data access permissions */
|
||||
uint32_t pmsav5_insn_ap; /* PMSAv5 MPU insn access permissions */
|
||||
uint32_t ifsr_el2; /* Fault status registers. */
|
||||
uint64_t esr_el1;
|
||||
uint32_t c6_region[8]; /* MPU base/size registers. */
|
||||
uint32_t c6_insn; /* Fault address registers. */
|
||||
uint32_t c6_data;
|
||||
uint32_t c7_par; /* Translation result. */
|
||||
uint32_t c7_par_hi; /* Translation result, high 32 bits */
|
||||
uint64_t far_el1; /* Fault address registers. */
|
||||
uint64_t par_el1; /* Translation result. */
|
||||
uint32_t c9_insn; /* Cache lockdown registers. */
|
||||
uint32_t c9_data;
|
||||
uint32_t c9_pmcr; /* performance monitor control register */
|
||||
@@ -202,7 +200,7 @@ typedef struct CPUARMState {
|
||||
uint64_t mair_el1;
|
||||
uint64_t c12_vbar; /* vector base address register */
|
||||
uint32_t c13_fcse; /* FCSE PID. */
|
||||
uint32_t c13_context; /* Context ID. */
|
||||
uint64_t contextidr_el1; /* Context ID. */
|
||||
uint64_t tpidr_el0; /* User RW Thread register. */
|
||||
uint64_t tpidrro_el0; /* User RO Thread register. */
|
||||
uint64_t tpidr_el1; /* Privileged Thread register. */
|
||||
@@ -238,6 +236,21 @@ typedef struct CPUARMState {
|
||||
int pending_exception;
|
||||
} v7m;
|
||||
|
||||
/* Information associated with an exception about to be taken:
|
||||
* code which raises an exception must set cs->exception_index and
|
||||
* the relevant parts of this structure; the cpu_do_interrupt function
|
||||
* will then set the guest-visible registers as part of the exception
|
||||
* entry process.
|
||||
*/
|
||||
struct {
|
||||
uint32_t syndrome; /* AArch64 format syndrome register */
|
||||
uint32_t fsr; /* AArch32 format fault status register info */
|
||||
uint64_t vaddress; /* virtual addr associated with exception, if any */
|
||||
/* If we implement EL2 we will also need to store information
|
||||
* about the intermediate physical address for stage 2 faults.
|
||||
*/
|
||||
} exception;
|
||||
|
||||
/* Thumb-2 EE state. */
|
||||
uint32_t teecr;
|
||||
uint32_t teehbr;
|
||||
@@ -322,11 +335,7 @@ typedef struct CPUARMState {
|
||||
#include "cpu-qom.h"
|
||||
|
||||
ARMCPU *cpu_arm_init(const char *cpu_model);
|
||||
void arm_translate_init(void);
|
||||
void arm_cpu_register_gdb_regs_for_features(ARMCPU *cpu);
|
||||
int cpu_arm_exec(CPUARMState *s);
|
||||
int bank_number(int mode);
|
||||
void switch_mode(CPUARMState *, int);
|
||||
uint32_t do_arm_semihosting(CPUARMState *env);
|
||||
|
||||
static inline bool is_a64(CPUARMState *env)
|
||||
@@ -425,6 +434,7 @@ int arm_cpu_handle_mmu_fault(CPUState *cpu, vaddr address, int rw,
|
||||
* Only these are valid when in AArch64 mode; in
|
||||
* AArch32 mode SPSRs are basically CPSR-format.
|
||||
*/
|
||||
#define PSTATE_SP (1U)
|
||||
#define PSTATE_M (0xFU)
|
||||
#define PSTATE_nRW (1U << 4)
|
||||
#define PSTATE_F (1U << 6)
|
||||
@@ -548,17 +558,6 @@ static inline void vfp_set_fpcr(CPUARMState *env, uint32_t val)
|
||||
vfp_set_fpscr(env, new_fpscr);
|
||||
}
|
||||
|
||||
enum arm_fprounding {
|
||||
FPROUNDING_TIEEVEN,
|
||||
FPROUNDING_POSINF,
|
||||
FPROUNDING_NEGINF,
|
||||
FPROUNDING_ZERO,
|
||||
FPROUNDING_TIEAWAY,
|
||||
FPROUNDING_ODD
|
||||
};
|
||||
|
||||
int arm_rmode_to_sf(int rmode);
|
||||
|
||||
enum arm_cpu_mode {
|
||||
ARM_CPU_MODE_USR = 0x10,
|
||||
ARM_CPU_MODE_FIQ = 0x11,
|
||||
@@ -572,6 +571,7 @@ enum arm_cpu_mode {
|
||||
/* VFP system registers. */
|
||||
#define ARM_VFP_FPSID 0
|
||||
#define ARM_VFP_FPSCR 1
|
||||
#define ARM_VFP_MVFR2 5
|
||||
#define ARM_VFP_MVFR1 6
|
||||
#define ARM_VFP_MVFR0 7
|
||||
#define ARM_VFP_FPEXC 8
|
||||
@@ -630,6 +630,7 @@ enum arm_features {
|
||||
ARM_FEATURE_V8_AES, /* implements AES part of v8 Crypto Extensions */
|
||||
ARM_FEATURE_CBAR, /* has cp15 CBAR */
|
||||
ARM_FEATURE_CRC, /* ARMv8 CRC instructions */
|
||||
ARM_FEATURE_CBAR_RO, /* has cp15 CBAR and it is read-only */
|
||||
};
|
||||
|
||||
static inline int arm_feature(CPUARMState *env, int feature)
|
||||
@@ -763,7 +764,8 @@ static inline uint64_t cpreg_to_kvm_id(uint32_t cpregid)
|
||||
#define ARM_CP_WFI (ARM_CP_SPECIAL | (2 << 8))
|
||||
#define ARM_CP_NZCV (ARM_CP_SPECIAL | (3 << 8))
|
||||
#define ARM_CP_CURRENTEL (ARM_CP_SPECIAL | (4 << 8))
|
||||
#define ARM_LAST_SPECIAL ARM_CP_CURRENTEL
|
||||
#define ARM_CP_DC_ZVA (ARM_CP_SPECIAL | (5 << 8))
|
||||
#define ARM_LAST_SPECIAL ARM_CP_DC_ZVA
|
||||
/* Used only as a terminator for ARMCPRegInfo lists */
|
||||
#define ARM_CP_SENTINEL 0xffff
|
||||
/* Mask of only the flag bits in a type field */
|
||||
@@ -1109,10 +1111,14 @@ static inline int cpu_mmu_index (CPUARMState *env)
|
||||
#define ARM_TBFLAG_CONDEXEC_MASK (0xff << ARM_TBFLAG_CONDEXEC_SHIFT)
|
||||
#define ARM_TBFLAG_BSWAP_CODE_SHIFT 16
|
||||
#define ARM_TBFLAG_BSWAP_CODE_MASK (1 << ARM_TBFLAG_BSWAP_CODE_SHIFT)
|
||||
#define ARM_TBFLAG_CPACR_FPEN_SHIFT 17
|
||||
#define ARM_TBFLAG_CPACR_FPEN_MASK (1 << ARM_TBFLAG_CPACR_FPEN_SHIFT)
|
||||
|
||||
/* Bit usage when in AArch64 state */
|
||||
#define ARM_TBFLAG_AA64_EL_SHIFT 0
|
||||
#define ARM_TBFLAG_AA64_EL_MASK (0x3 << ARM_TBFLAG_AA64_EL_SHIFT)
|
||||
#define ARM_TBFLAG_AA64_FPEN_SHIFT 2
|
||||
#define ARM_TBFLAG_AA64_FPEN_MASK (1 << ARM_TBFLAG_AA64_FPEN_SHIFT)
|
||||
|
||||
/* some convenience accessor macros */
|
||||
#define ARM_TBFLAG_AARCH64_STATE(F) \
|
||||
@@ -1131,16 +1137,25 @@ static inline int cpu_mmu_index (CPUARMState *env)
|
||||
(((F) & ARM_TBFLAG_CONDEXEC_MASK) >> ARM_TBFLAG_CONDEXEC_SHIFT)
|
||||
#define ARM_TBFLAG_BSWAP_CODE(F) \
|
||||
(((F) & ARM_TBFLAG_BSWAP_CODE_MASK) >> ARM_TBFLAG_BSWAP_CODE_SHIFT)
|
||||
#define ARM_TBFLAG_CPACR_FPEN(F) \
|
||||
(((F) & ARM_TBFLAG_CPACR_FPEN_MASK) >> ARM_TBFLAG_CPACR_FPEN_SHIFT)
|
||||
#define ARM_TBFLAG_AA64_EL(F) \
|
||||
(((F) & ARM_TBFLAG_AA64_EL_MASK) >> ARM_TBFLAG_AA64_EL_SHIFT)
|
||||
#define ARM_TBFLAG_AA64_FPEN(F) \
|
||||
(((F) & ARM_TBFLAG_AA64_FPEN_MASK) >> ARM_TBFLAG_AA64_FPEN_SHIFT)
|
||||
|
||||
static inline void cpu_get_tb_cpu_state(CPUARMState *env, target_ulong *pc,
|
||||
target_ulong *cs_base, int *flags)
|
||||
{
|
||||
int fpen = extract32(env->cp15.c1_coproc, 20, 2);
|
||||
|
||||
if (is_a64(env)) {
|
||||
*pc = env->pc;
|
||||
*flags = ARM_TBFLAG_AARCH64_STATE_MASK
|
||||
| (arm_current_pl(env) << ARM_TBFLAG_AA64_EL_SHIFT);
|
||||
if (fpen == 3 || (fpen == 1 && arm_current_pl(env) != 0)) {
|
||||
*flags |= ARM_TBFLAG_AA64_FPEN_MASK;
|
||||
}
|
||||
} else {
|
||||
int privmode;
|
||||
*pc = env->regs[15];
|
||||
@@ -1157,9 +1172,13 @@ static inline void cpu_get_tb_cpu_state(CPUARMState *env, target_ulong *pc,
|
||||
if (privmode) {
|
||||
*flags |= ARM_TBFLAG_PRIV_MASK;
|
||||
}
|
||||
if (env->vfp.xregs[ARM_VFP_FPEXC] & (1 << 30)) {
|
||||
if (env->vfp.xregs[ARM_VFP_FPEXC] & (1 << 30)
|
||||
|| arm_el_is_aa64(env, 1)) {
|
||||
*flags |= ARM_TBFLAG_VFPEN_MASK;
|
||||
}
|
||||
if (fpen == 3 || (fpen == 1 && arm_current_pl(env) != 0)) {
|
||||
*flags |= ARM_TBFLAG_CPACR_FPEN_MASK;
|
||||
}
|
||||
}
|
||||
|
||||
*cs_base = 0;
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user