summaryrefslogtreecommitdiffstats
path: root/scripts
Commit message (Collapse)AuthorAgeFilesLines
* qapi-types: Bury code dead since commit 6b5abc7Markus Armbruster2015-06-181-6/+2
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi-types: Split generate_fwd_builtin() off generate_fwd_struct()Markus Armbruster2015-06-181-6/+6
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi-types: Drop unused members parametersMarkus Armbruster2015-06-181-7/+7
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi-types: Don't filter out expressions with 'gen'Markus Armbruster2015-06-181-1/+0
| | | | | | | | Useless, because it can only occur in commands, and we're not dealing with commands here. Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Catch and reject flat union branch of array typeMarkus Armbruster2015-06-181-1/+1
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Better separate the different kinds of helpersMarkus Armbruster2015-06-181-54/+74
| | | | | | | | | | Insert comments to separate sections dealing with parsing, semantic analysis, code generation, and so forth. Move helpers to their proper section. Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Move exprs checking from parse_schema() to check_exprs()Markus Armbruster2015-06-181-76/+66
| | | | | | | To have expression semantic analysis in one place rather than two. Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Fix to reject stray 't', 'f' and 'n'Markus Armbruster2015-06-181-14/+12
| | | | | | | Screwed up in commit e53188a. Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Simplify inclusion cycle detectionMarkus Armbruster2015-06-181-10/+8
| | | | | | | | | | | We maintain a stack of filenames in include_hist for convenient cycle detection. As error_path() demonstrates, the same information is readily available in the expr_info, so just use that, and drop include_hist. Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Fix file name in error messages for included filesMarkus Armbruster2015-06-181-4/+3
| | | | | | | | | We print the name as it appears in the include expression. Tools processing error messages want it relative to the working directory. Make it so. Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Improve a couple of confusing variable namesMarkus Armbruster2015-06-181-22/+23
| | | | | | | | | | | | | old name new name ---------------------------- input_file fname input_relname fname input_fname abs_fname include_path incl_abs_fname parent_info incl_info Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Eliminate superfluous QAPISchema attribute input_dirMarkus Armbruster2015-06-181-2/+2
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* Teach analyze-migration.py about section footersDr. David Alan Gilbert2015-06-121-0/+5
| | | | | Signed-off-by: Dr. David Alan Gilbert <dgilbert@redhat.com> Signed-off-by: Juan Quintela <quintela@redhat.com>
* virtio-input: add linux/input.hGerd Hoffmann2015-05-291-1/+3
| | | | | | Linux input layer (evdev) header file. Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
* qapi: Inline gen_command_decl_prologue(), gen_command_def_prologue()Markus Armbruster2015-05-141-34/+24
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Drop pointless flush() before close()Markus Armbruster2015-05-141-4/+0
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Factor open_output(), close_output() out of generatorsMarkus Armbruster2015-05-145-215/+141
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Turn generators' mandatory option -i into an argumentMarkus Armbruster2015-05-141-7/+5
| | | | | | | | | Mandatory option is silly, and the error handling is missing: the programs crash when -i isn't supplied. Make it an argument, and check it properly. Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Fix generators to report command line errors decentlyMarkus Armbruster2015-05-141-1/+5
| | | | | | | | Report to stderr, prefix with the program name. Also reject extra arguments. Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Factor parse_command_line() out of the generatorsMarkus Armbruster2015-05-145-125/+52
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: qapi-commands.py option --type is unused, drop itMarkus Armbruster2015-05-141-36/+32
| | | | | | | | | | | | | | | | Anything but --type sync (which is the default) suppresses output entirely, which makes no sense. Dates back to the initial commit c17d990. Commit message says "Currently only generators for synchronous qapi/qmp functions are supported", so maybe output other than "synchronous qapi/qmp" was planned at the time, to be selected with --type. Should other kinds of output ever materialize, we can put the option back. Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: qapi-event.py option -b does nothing, drop itMarkus Armbruster2015-05-141-5/+2
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com>
* qapi: Support downstream events and commandsEric Blake2015-05-141-11/+5
| | | | | | | | | | | Enhance the testsuite to cover downstream events and commands. Events worked without more tweaks, but commands needed a few final updates in the generator to mangle names in the appropriate places. In making those tweaks, it was easier to drop type_visitor() and inline its actions instead. Signed-off-by: Eric Blake <eblake@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Support downstream alternatesEric Blake2015-05-142-6/+7
| | | | | | | | | Enhance the testsuite to cover downstream alternates, including whether the branch name or type is downstream. Update the generator to mangle alternate names in the appropriate places. Signed-off-by: Eric Blake <eblake@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Support downstream flat unionsEric Blake2015-05-142-3/+3
| | | | | | | | | | Enhance the testsuite to cover downstream flat unions, including the base type, discriminator name and type, and branch name and type. Update the generator to mangle the union names in the appropriate places. Signed-off-by: Eric Blake <eblake@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Support downstream simple unionsEric Blake2015-05-142-5/+5
| | | | | | | | | Enhance the testsuite to cover downstream simple unions, including when a union branch is a downstream name. Update the generator to mangle the union names in the appropriate places. Signed-off-by: Eric Blake <eblake@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Support downstream structsEric Blake2015-05-142-7/+8
| | | | | | | | | Enhance the testsuite to cover downstream structs, including struct members and base structs. Update the generator to mangle the struct names in the appropriate places. Signed-off-by: Eric Blake <eblake@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Support downstream enumsEric Blake2015-05-142-11/+12
| | | | | | | | | Enhance the testsuite to cover a downstream enum type and enum string. Update the generator to mangle the enum name in the appropriate places. Signed-off-by: Eric Blake <eblake@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Make c_type() consistently convert qapi namesEric Blake2015-05-141-4/+29
| | | | | | | | | | | | | | | | | | | | | | | | | | Continuing the string of cleanups for supporting downstream names containing '.', this patch focuses on ensuring c_type() can handle a downstream name. This patch alone does not fix the places where generator output should be calling this function but was open-coding things instead, but it gets us a step closer. In particular, the changes to c_list_type() and type_name() mean that type_name(FOO) now handles the case when FOO contains '.', '-', or is a ticklish identifier other than a builtin (builtins are exempted because ['int'] must remain mapped to 'intList' and not 'q_intList'). Meanwhile, ['unix'] now maps to 'q_unixList' rather than 'unixList', to match the fact that 'unix' is ticklish; however, our naming conventions state that complex types should start with a capital, so no type name following conventions will ever have the 'q_' prepended. Likewise, changes to c_type() mean that c_type(FOO) properly handles an enum or complex type FOO with '.' or '-' in the name, or is a ticklish identifier (again, a ticklish identifier as a type name violates conventions). Signed-off-by: Eric Blake <eblake@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Tidy c_type() logicEric Blake2015-05-141-28/+30
| | | | | | | | | | | c_type() is designed to be called on both string names and on array designations, so 'name' is a bit misleading because it operates on more than strings. Also, no caller ever passes an empty string. Finally, + notation is a bit nicer to read than '%s' % value for string concatenation. Signed-off-by: Eric Blake <eblake@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Move camel_to_upper(), c_enum_const() to closely related codeMarkus Armbruster2015-05-141-25/+25
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Eric Blake <eblake@redhat.com>
* qapi: Use c_enum_const() in generate_alternate_qtypes()Markus Armbruster2015-05-142-15/+2
| | | | | | | Missed in commit b0b5819. Signed-off-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Eric Blake <eblake@redhat.com>
* qapi: Simplify c_enum_const()Markus Armbruster2015-05-141-3/+1
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Eric Blake <eblake@redhat.com>
* qapi: Rename generate_enum_full_value() to c_enum_const()Markus Armbruster2015-05-144-11/+10
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Eric Blake <eblake@redhat.com>
* qapi: Rename _generate_enum_string() to camel_to_upper()Markus Armbruster2015-05-141-6/+6
| | | | | Signed-off-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Eric Blake <eblake@redhat.com>
* qapi: Rename identical c_fun()/c_var() into c_name()Eric Blake2015-05-145-38/+36
| | | | | | | | | | | Now that the two functions are identical, we only need one of them, and we might as well give it a more descriptive name. Basically, the function serves as the translation from a QAPI name into a (portion of a) C identifier, without regards to whether it is a variable or function name. Signed-off-by: Eric Blake <eblake@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Fix C identifiers generated for names containing '.'Markus Armbruster2015-05-141-2/+5
| | | | | | | | | | | | | | | | | | | | | c_fun() maps '.' to '_', c_var() doesn't. Nothing prevents '.' in QAPI names that get passed to c_var(). Which QAPI names get passed to c_fun(), to c_var(), or to both is not obvious. Names of command parameters and struct type members get passed to c_var(). c_var() strips a leading '*', but this cannot happen. c_fun() doesn't. Fix c_var() to work exactly like c_fun(). Perhaps they should be replaced by a single mapping function. Signed-off-by: Markus Armbruster <armbru@redhat.com> [add 'import string'] Signed-off-by: Eric Blake <eblake@redhat.com> Reviewed-by: Alberto Garcia <berto@igalia.com>
* scripts: qmp-shell: Add verbose flagJohn Snow2015-05-111-6/+18
| | | | | | | | | | | | | | | | | | | Add a verbose flag that shows the QMP command that was constructed, to allow for later copy/pasting, reference, debugging, etc. The QMP is converted from a Python literal to JSON first, to ensure that it is viable input to the actual QMP parser. As a side-effect, this JSON output will helpfully show all the necessary conversions that were performed on the input, illustrating that "True" was transformed back into "true", literal values are now escaped with "" instead of '', and so on. Signed-off-by: John Snow <jsnow@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com> Tested-by: Kashyap Chamarthy <kchamart@redhat.com> Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
* scripts: qmp-shell: add transaction subshellJohn Snow2015-05-111-1/+41
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Add a special processing mode to craft transactions. By entering "transaction(" the shell will enter a special mode where each subsequent command will be saved as a transaction instead of executed as an individual command. The transaction can be submitted by entering ")" on a line by itself. Examples: Separate lines: (QEMU) transaction( TRANS> block-dirty-bitmap-add node=drive0 name=bitmap1 TRANS> block-dirty-bitmap-clear node=drive0 name=bitmap0 TRANS> ) With a transaction action included on the first line: (QEMU) transaction( block-dirty-bitmap-add node=drive0 name=bitmap2 TRANS> block-dirty-bitmap-add node=drive0 name=bitmap3 TRANS> ) As a one-liner, with just one transaction action: (QEMU) transaction( block-dirty-bitmap-add node=drive0 name=bitmap0 ) As a side-effect of this patch, blank lines are now parsed as no-ops, regardless of which shell mode you are in. Signed-off-by: John Snow <jsnow@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com> Tested-by: Kashyap Chamarthy <kchamart@redhat.com> Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
* scripts: qmp-shell: Expand support for QMP expressionsJohn Snow2015-05-111-16/+47
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | This includes support for [] expressions, single-quotes in QMP expressions (which is not strictly a part of JSON), and the ability to use "True", "False" and "None" literals instead of JSON's equivalent true, false, and null literals. qmp-shell currently allows you to describe values as JSON expressions: key={"key":{"key2":"val"}} But it does not currently support arrays, which are needed for serializing and deserializing transactions: key=[{"type":"drive-backup","data":{...}}] qmp-shell also only currently accepts doubly quoted strings as-per JSON spec, but QMP allows single quotes. Lastly, python allows you to utilize "True" or "False" as boolean literals, but JSON expects "true" or "false". Expand qmp-shell to allow the user to type either, converting to the correct type. As a consequence of the above, the key=val parsing is also improved to give better error messages if a key=val token is not provided. CAVEAT: The parser is still extremely rudimentary and does not expect to find spaces in {} nor [] expressions. This patch does not improve this functionality. Signed-off-by: John Snow <jsnow@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com> Tested-by: Kashyap Chamarthy <kchamart@redhat.com> Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
* scripts: qmp-shell: refactor helpersJohn Snow2015-05-111-11/+13
| | | | | | | | | | | Refactor the qmp-shell command line processing function into two components. This will be used to allow sub-expressions, which will assist us in adding transactional support to qmp-shell. Signed-off-by: John Snow <jsnow@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com> Tested-by: Kashyap Chamarthy <kchamart@redhat.com> Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
* qapi: Check for member name conflicts with a base classEric Blake2015-05-051-1/+22
| | | | | | | | | | | | | | | | | | | | Our type inheritance for both 'struct' and for flat 'union' merges key/value pairs from the base class with those from the type in question. Although the C code currently boxes things so that there is a distinction between which member is referred to, the QMP wire format does not allow passing a key more than once in a single object. Besides, if we ever change the generated C code to not be quite so boxy, we'd want to avoid duplicate member names there, too. Fix a testsuite entry added in an earlier patch, as well as adding a couple more tests to ensure we have appropriate coverage. Ensure that collisions are detected, regardless of whether there is a difference in opinion on whether the member name is optional. Signed-off-by: Eric Blake <eblake@redhat.com> Reviewed-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Support (subset of) \u escapes in stringsEric Blake2015-05-051-1/+35
| | | | | | | | | | | | | | | | | | | | | | | | | | The handling of \ inside QAPI strings was less than ideal, and really only worked JSON's \/, \\, \", and our extension of \' (an obvious extension, when you realize we use '' instead of "" for strings). For other things, like '\n', it resulted in a literal 'n' instead of a newline. Of course, at the moment, we really have no use for escaped characters, as QAPI has to map to C identifiers, and we currently support ASCII only for that. But down the road, we may add support for default values for string parameters to a command or struct; if that happens, it would be nice to correctly support all JSON escape sequences, such as \n or \uXXXX. This gets us closer, by supporting Unicode escapes in the ASCII range. Since JSON does not require \OCTAL or \xXX escapes, and our QMP implementation does not understand them either, I intentionally reject it here, but it would be an easy addition if we desired it. Likewise, intentionally refusing the NUL byte means we don't have to worry about C strings being shorter than the qapi input. Signed-off-by: Eric Blake <eblake@redhat.com> Reviewed-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Drop dead visitor code related to nested structsEric Blake2015-05-051-37/+12
| | | | | | | | | | Now that we no longer have nested structs to visit, the use of prefix strings is no longer required. Remove the code that is no longer reachable. Signed-off-by: Eric Blake <eblake@redhat.com> Reviewed-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Drop support for inline nested typesEric Blake2015-05-055-58/+20
| | | | | | | | | | | | | | A future patch will be using a 'name':{dictionary} entry in the QAPI schema to specify a default value for an optional argument (see previous commit messages for more details why); but existing use of inline nested structs conflicts with that goal. Now that all commands have been changed to avoid inline nested structs, nuke support for them, and turn it into a hard error. Update the testsuite to reflect tighter parsing rules. Signed-off-by: Eric Blake <eblake@redhat.com> Reviewed-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Forbid 'type' in schemaEric Blake2015-05-051-14/+0
| | | | | | | | | | | | Referring to "type" as both a meta-type (built-in, enum, union, alternate, or struct) and a specific type (the name that the schema uses for declaring structs) is confusing. Finish up the conversion to using "struct" in qapi schema by removing the hack in the generator that allowed 'type'. Signed-off-by: Eric Blake <eblake@redhat.com> Reviewed-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Prefer 'struct' over 'type' in generatorEric Blake2015-05-053-29/+41
| | | | | | | | | | | | | | | | | | | | | | | Referring to "type" as both a meta-type (built-in, enum, union, alternate, or struct) and a specific type (the name that the schema uses for declaring structs) is confusing. The confusion is only made worse by the fact that the generator mostly already refers to struct even when dealing with expr['type']. This commit changes the generator to consistently refer to it as struct everywhere, plus a single back-compat tweak that allows accepting the existing .json files as-is, so that the meat of this change is separate from the mindless churn of that change. Fix the testsuite fallout for error messages that change, and in some cases, become more legible. Improve comments to better match our intentions where a struct (rather than any complex type) is required. Note that in some cases, an error message now refers to 'struct' while the schema still refers to 'type'; that will be cleaned up in the later commit to the schema. Signed-off-by: Eric Blake <eblake@redhat.com> Reviewed-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: More rigorous checking for type safety bypassEric Blake2015-05-051-5/+17
| | | | | | | | | | | | | | | | | | | | Now that we have a way to validate every type, we can also be stricter about enforcing that callers that want to bypass type safety in generated code. Prior to this patch, it didn't matter what value was associated with the key 'gen', but it looked odd that 'gen':'yes' could result in bypassing the generated code. These changes also enforce the changes made earlier in the series for documentation and consolidation of using '**' as the wildcard type, as well as 'gen':false as the canonical spelling for requesting type bypass. Note that 'gen':false is a one-way switch away from the default; we do not support 'gen':true (similar for 'success-response'). In practice, this doesn't matter. Signed-off-by: Eric Blake <eblake@redhat.com> Reviewed-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Whitelist commands that don't return dictionaryEric Blake2015-05-051-3/+28
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | ...or an array of dictionaries. Although we have to cater to existing commands, returning a non-dictionary means the command is not extensible (no new name/value pairs can be added if more information must be returned in parallel). By making the whitelist explicit, any new command that falls foul of this practice will have to be self-documenting, which will encourage developers to either justify the action or rework the design to use a dictionary after all. It's a little bit sloppy that we share a single whitelist among three clients (it's too permissive for each). If this is a problem, a future patch could tighten things by having the generator take the whitelist as an argument (as in scripts/qapi-commands.py --legacy-returns=...), or by having the generator output C code that requires explicit use of the whitelist (as in: #ifndef FROBNICATE_LEGACY_RETURN_OK # error Command 'frobnicate' should return a dictionary #endif then having the callers define appropriate macros). But until we need such fine-grained separation (if ever), this patch does the job just fine. Signed-off-by: Eric Blake <eblake@redhat.com> Reviewed-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
* qapi: Require valid namesEric Blake2015-05-051-17/+46
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | Previous commits demonstrated that the generator overlooked various bad naming situations: - types, commands, and events need a valid name - enum members must be valid names, when combined with prefix - union and alternate branches cannot be marked optional Valid upstream names match [a-zA-Z][a-zA-Z0-9_-]*; valid downstream names match __[a-zA-Z][a-zA-Z0-9._-]*. Enumerations match the weaker [a-zA-Z0-9._-]+ (in part thanks to QKeyCode picking an enum that starts with a digit, which we can't change now due to backwards compatibility). Rather than call out three separate regex, this patch just uses a broader combination that allows both upstream and downstream names, as well as a small hack that realizes that any enum name is merely a suffix to an already valid name prefix (that is, any enum name is valid if prepending _ fits the normal rules). We could reject new enumeration names beginning with a digit by whitelisting existing exceptions. We could also be stricter about the distinction between upstream names (no leading underscore, no use of dot) and downstream (mandatory leading double underscore), but it is probably not worth the bother. Signed-off-by: Eric Blake <eblake@redhat.com> Reviewed-by: Markus Armbruster <armbru@redhat.com> Signed-off-by: Markus Armbruster <armbru@redhat.com>
OpenPOWER on IntegriCloud