On Mon, Jul 17, 2006 at 01:50:25PM +0100, Daniel P. Berrange wrote:
On Tue, Jul 11, 2006 at 10:50:53AM -0400, Daniel Veillard wrote:
> We still have a relatively simple API for the common case, and for special
> cases we have an extension capability with relatively clear definitions. it's
> a bitstrange but I think that should cover most case as best as possible
I dont particularly like this as an API because I think it will be error
prone for application developers. Most app developers will only ever have
a handful of CPUs in their test machines, so they'll never the alternate
codepath for > 256 cpu case. Likewise I don't like the idea of a virVcpuInfo
struct which has a variable size because it will totally confuse people who
haven't read the API docs very carefully, again leading to obscure bugs.
The root problem is that we have two conflicting goals here
1. Want to have virVcpuInfo be a fixed size struct
2. We want a cpumap of arbitrary size
Right this is confusing, I wanted to avoid another allocation in the general
case but this made things even more confusing.
The obvious solution to this problem is to *remove* the cpumap data
from
the virVcpuInfo structure completely, and always pass in a separately
malloc'd array of the correct size. So I'd suggest:
typedef struct _virVcpuInfo virVcpuInfo;
struct _virVcpuInfo {
unsigned int number; /* virtual CPU number */
int state; /* value from virVcpuState */
unsigned long long cpuTime; /* CPU time used, in nanoseconds */
int cpu; /* real CPU number, or -1 if offline */
}
virDomainGetVcpus(virDomainPtr domain, virVcpuInfoPtr info, int maxinfo,
char *cpumap, int maplen);
Agreed, this is the most logical approach
The client applications calling this API already have to malloc() the memory
region for the 'info' parameter of a correct size, so having to also malloc
the cpumap parameter is no extra trouble.
virDomainInfo info;
virDomainVpuInfoPtr cpuInfo;
int cpuMapLen;
char *cpuMap;
virDomainGetInfo(domain, &info);
cpuInfo = malloc(sizeof(virDomainVcpuInfo)*info.nrVirtCpu);
cpuMapLen = (info.nrVirtCpu + 7) / 8 ;
cpuMap = malloc(cpuMapLen);
virDomainGetVCpus(domain, cpuInfo, info.nrVirtCpu, cpuMap, cpuMapLen);
... do stuff with the data ...
free(cpuInfo);
free(cpuMap);
So you can see there is minimal extra work to always pass in cpuMap as
a separate parameter. If an application didn't care about the cpuMap
data they could simply pass in NULL.
Agree. We should keep an example of use (like above completed) in the source
tree to help developpers.
Daniel
--
Daniel Veillard | Red Hat
http://redhat.com/
veillard(a)redhat.com | libxml GNOME XML XSLT toolkit
http://xmlsoft.org/
http://veillard.com/ | Rpmfind RPM search engine
http://rpmfind.net/