pax_global_header00006660000000000000000000000064131556367210014523gustar00rootroot0000000000000052 comment=7cb788c9c43facfd2d14ff50e16d6a19f033a6a7 bluez-tools-2.0~20170911.0.7cb788c/000077500000000000000000000000001315563672100161105ustar00rootroot00000000000000bluez-tools-2.0~20170911.0.7cb788c/.gitignore000066400000000000000000000005001315563672100200730ustar00rootroot00000000000000nbproject/ *.o .deps .dirstamp .version .dep.inc Makefile Makefile-bluez-tools.mk Makefile.in aclocal.m4 autom4te.cache/ compile config.* configure depcomp install-sh missing src/bt-adapter src/bt-agent src/bt-audio src/bt-device src/bt-input src/bt-monitor src/bt-network src/bt-obex src/bt-serial stamp-h1 test_* tmp/ bluez-tools-2.0~20170911.0.7cb788c/AUTHORS000066400000000000000000000001711315563672100171570ustar00rootroot00000000000000Alexander Orlenko Scott Conover Daniel Sills bluez-tools-2.0~20170911.0.7cb788c/COPYING000066400000000000000000000431261315563672100171510ustar00rootroot00000000000000 GNU GENERAL PUBLIC LICENSE Version 2, June 1991 Copyright (C) 1989, 1991 Free Software Foundation, Inc. 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA Everyone is permitted to copy and distribute verbatim copies of this license document, but changing it is not allowed. Preamble The licenses for most software are designed to take away your freedom to share and change it. By contrast, the GNU General Public License is intended to guarantee your freedom to share and change free software--to make sure the software is free for all its users. This General Public License applies to most of the Free Software Foundation's software and to any other program whose authors commit to using it. (Some other Free Software Foundation software is covered by the GNU Library General Public License instead.) You can apply it to your programs, too. When we speak of free software, we are referring to freedom, not price. Our General Public Licenses are designed to make sure that you have the freedom to distribute copies of free software (and charge for this service if you wish), that you receive source code or can get it if you want it, that you can change the software or use pieces of it in new free programs; and that you know you can do these things. To protect your rights, we need to make restrictions that forbid anyone to deny you these rights or to ask you to surrender the rights. These restrictions translate to certain responsibilities for you if you distribute copies of the software, or if you modify it. For example, if you distribute copies of such a program, whether gratis or for a fee, you must give the recipients all the rights that you have. You must make sure that they, too, receive or can get the source code. And you must show them these terms so they know their rights. We protect your rights with two steps: (1) copyright the software, and (2) offer you this license which gives you legal permission to copy, distribute and/or modify the software. Also, for each author's protection and ours, we want to make certain that everyone understands that there is no warranty for this free software. If the software is modified by someone else and passed on, we want its recipients to know that what they have is not the original, so that any problems introduced by others will not reflect on the original authors' reputations. Finally, any free program is threatened constantly by software patents. We wish to avoid the danger that redistributors of a free program will individually obtain patent licenses, in effect making the program proprietary. To prevent this, we have made it clear that any patent must be licensed for everyone's free use or not licensed at all. The precise terms and conditions for copying, distribution and modification follow. GNU GENERAL PUBLIC LICENSE TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION 0. This License applies to any program or other work which contains a notice placed by the copyright holder saying it may be distributed under the terms of this General Public License. The "Program", below, refers to any such program or work, and a "work based on the Program" means either the Program or any derivative work under copyright law: that is to say, a work containing the Program or a portion of it, either verbatim or with modifications and/or translated into another language. (Hereinafter, translation is included without limitation in the term "modification".) Each licensee is addressed as "you". Activities other than copying, distribution and modification are not covered by this License; they are outside its scope. The act of running the Program is not restricted, and the output from the Program is covered only if its contents constitute a work based on the Program (independent of having been made by running the Program). Whether that is true depends on what the Program does. 1. You may copy and distribute verbatim copies of the Program's source code as you receive it, in any medium, provided that you conspicuously and appropriately publish on each copy an appropriate copyright notice and disclaimer of warranty; keep intact all the notices that refer to this License and to the absence of any warranty; and give any other recipients of the Program a copy of this License along with the Program. You may charge a fee for the physical act of transferring a copy, and you may at your option offer warranty protection in exchange for a fee. 2. You may modify your copy or copies of the Program or any portion of it, thus forming a work based on the Program, and copy and distribute such modifications or work under the terms of Section 1 above, provided that you also meet all of these conditions: a) You must cause the modified files to carry prominent notices stating that you changed the files and the date of any change. b) You must cause any work that you distribute or publish, that in whole or in part contains or is derived from the Program or any part thereof, to be licensed as a whole at no charge to all third parties under the terms of this License. c) If the modified program normally reads commands interactively when run, you must cause it, when started running for such interactive use in the most ordinary way, to print or display an announcement including an appropriate copyright notice and a notice that there is no warranty (or else, saying that you provide a warranty) and that users may redistribute the program under these conditions, and telling the user how to view a copy of this License. (Exception: if the Program itself is interactive but does not normally print such an announcement, your work based on the Program is not required to print an announcement.) These requirements apply to the modified work as a whole. If identifiable sections of that work are not derived from the Program, and can be reasonably considered independent and separate works in themselves, then this License, and its terms, do not apply to those sections when you distribute them as separate works. But when you distribute the same sections as part of a whole which is a work based on the Program, the distribution of the whole must be on the terms of this License, whose permissions for other licensees extend to the entire whole, and thus to each and every part regardless of who wrote it. Thus, it is not the intent of this section to claim rights or contest your rights to work written entirely by you; rather, the intent is to exercise the right to control the distribution of derivative or collective works based on the Program. In addition, mere aggregation of another work not based on the Program with the Program (or with a work based on the Program) on a volume of a storage or distribution medium does not bring the other work under the scope of this License. 3. You may copy and distribute the Program (or a work based on it, under Section 2) in object code or executable form under the terms of Sections 1 and 2 above provided that you also do one of the following: a) Accompany it with the complete corresponding machine-readable source code, which must be distributed under the terms of Sections 1 and 2 above on a medium customarily used for software interchange; or, b) Accompany it with a written offer, valid for at least three years, to give any third party, for a charge no more than your cost of physically performing source distribution, a complete machine-readable copy of the corresponding source code, to be distributed under the terms of Sections 1 and 2 above on a medium customarily used for software interchange; or, c) Accompany it with the information you received as to the offer to distribute corresponding source code. (This alternative is allowed only for noncommercial distribution and only if you received the program in object code or executable form with such an offer, in accord with Subsection b above.) The source code for a work means the preferred form of the work for making modifications to it. For an executable work, complete source code means all the source code for all modules it contains, plus any associated interface definition files, plus the scripts used to control compilation and installation of the executable. However, as a special exception, the source code distributed need not include anything that is normally distributed (in either source or binary form) with the major components (compiler, kernel, and so on) of the operating system on which the executable runs, unless that component itself accompanies the executable. If distribution of executable or object code is made by offering access to copy from a designated place, then offering equivalent access to copy the source code from the same place counts as distribution of the source code, even though third parties are not compelled to copy the source along with the object code. 4. You may not copy, modify, sublicense, or distribute the Program except as expressly provided under this License. Any attempt otherwise to copy, modify, sublicense or distribute the Program is void, and will automatically terminate your rights under this License. However, parties who have received copies, or rights, from you under this License will not have their licenses terminated so long as such parties remain in full compliance. 5. You are not required to accept this License, since you have not signed it. However, nothing else grants you permission to modify or distribute the Program or its derivative works. These actions are prohibited by law if you do not accept this License. Therefore, by modifying or distributing the Program (or any work based on the Program), you indicate your acceptance of this License to do so, and all its terms and conditions for copying, distributing or modifying the Program or works based on it. 6. Each time you redistribute the Program (or any work based on the Program), the recipient automatically receives a license from the original licensor to copy, distribute or modify the Program subject to these terms and conditions. You may not impose any further restrictions on the recipients' exercise of the rights granted herein. You are not responsible for enforcing compliance by third parties to this License. 7. If, as a consequence of a court judgment or allegation of patent infringement or for any other reason (not limited to patent issues), conditions are imposed on you (whether by court order, agreement or otherwise) that contradict the conditions of this License, they do not excuse you from the conditions of this License. If you cannot distribute so as to satisfy simultaneously your obligations under this License and any other pertinent obligations, then as a consequence you may not distribute the Program at all. For example, if a patent license would not permit royalty-free redistribution of the Program by all those who receive copies directly or indirectly through you, then the only way you could satisfy both it and this License would be to refrain entirely from distribution of the Program. If any portion of this section is held invalid or unenforceable under any particular circumstance, the balance of the section is intended to apply and the section as a whole is intended to apply in other circumstances. It is not the purpose of this section to induce you to infringe any patents or other property right claims or to contest validity of any such claims; this section has the sole purpose of protecting the integrity of the free software distribution system, which is implemented by public license practices. Many people have made generous contributions to the wide range of software distributed through that system in reliance on consistent application of that system; it is up to the author/donor to decide if he or she is willing to distribute software through any other system and a licensee cannot impose that choice. This section is intended to make thoroughly clear what is believed to be a consequence of the rest of this License. 8. If the distribution and/or use of the Program is restricted in certain countries either by patents or by copyrighted interfaces, the original copyright holder who places the Program under this License may add an explicit geographical distribution limitation excluding those countries, so that distribution is permitted only in or among countries not thus excluded. In such case, this License incorporates the limitation as if written in the body of this License. 9. The Free Software Foundation may publish revised and/or new versions of the General Public License from time to time. Such new versions will be similar in spirit to the present version, but may differ in detail to address new problems or concerns. Each version is given a distinguishing version number. If the Program specifies a version number of this License which applies to it and "any later version", you have the option of following the terms and conditions either of that version or of any later version published by the Free Software Foundation. If the Program does not specify a version number of this License, you may choose any version ever published by the Free Software Foundation. 10. If you wish to incorporate parts of the Program into other free programs whose distribution conditions are different, write to the author to ask for permission. For software which is copyrighted by the Free Software Foundation, write to the Free Software Foundation; we sometimes make exceptions for this. Our decision will be guided by the two goals of preserving the free status of all derivatives of our free software and of promoting the sharing and reuse of software generally. NO WARRANTY 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. END OF TERMS AND CONDITIONS How to Apply These Terms to Your New Programs If you develop a new program, and you want it to be of the greatest possible use to the public, the best way to achieve this is to make it free software which everyone can redistribute and change under these terms. To do so, attach the following notices to the program. It is safest to attach them to the start of each source file to most effectively convey the exclusion of warranty; and each file should have at least the "copyright" line and a pointer to where the full notice is found. Copyright (C) This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA Also add information on how to contact you by electronic and paper mail. If the program is interactive, make it output a short notice like this when it starts in an interactive mode: Gnomovision version 69, Copyright (C) year name of author Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'. This is free software, and you are welcome to redistribute it under certain conditions; type `show c' for details. The hypothetical commands `show w' and `show c' should show the appropriate parts of the General Public License. Of course, the commands you use may be called something other than `show w' and `show c'; they could even be mouse-clicks or menu items--whatever suits your program. You should also get your employer (if you work as a programmer) or your school, if any, to sign a "copyright disclaimer" for the program, if necessary. Here is a sample; alter the names: Yoyodyne, Inc., hereby disclaims all copyright interest in the program `Gnomovision' (which makes passes at compilers) written by James Hacker. , 1 April 1989 Ty Coon, President of Vice This General Public License does not permit incorporating your program into proprietary programs. If your program is a subroutine library, you may consider it more useful to permit linking proprietary applications with the library. If this is what you want to do, use the GNU Library General Public License instead of this License. bluez-tools-2.0~20170911.0.7cb788c/ChangeLog000066400000000000000000000047571315563672100176770ustar00rootroot00000000000000-------------------------- Changes in 0.2.0 (beta) - Replaced the DBus-GLib API with the GLib GIO GDBus API. DBus-GLib has been flagged as obsolete by freedesktop.org. DBus-GLib has also proved to be difficult when setting up DBus proxies to the newer BlueZ 5 API and thus been dropped in favor of the currently active GDBus API. - The use of GValue has been dropped in favor of GVariant. GVariants are used extensivly by the GDBus API as they are seriallized objects that are used for messaging DBus. - Because of the use of GDBus and GVariants, the need for custom C based marshallers have been dropped. Therefore, marshallers.c and marshallers.h have been deleted. - The use of GHashTables by proxies and DBus objects have been dropped in favor of GVariant-based dictionaries. GHashTables are still used in some portions of the source code but all DBus dictionaries returned will be GVariants. - Due to a major change in the BlueZ API (BlueZ 5), object properties are now stored in nodes with the `org.freedesktop.DBus.Properties' interface. A seperate GDBus proxy will be created for each BlueZ DBus object. - Due to a major change in the BlueZ API (BlueZ 5), the `org.freedesktop.DBus.ObjectManager' will be used to get properties, adapters, the default adapter, and changes to the BlueZ DBus objects (such as devices discovered). - The use of g_signal and its callbacks have been replaced in favor of g_dbus_connection_signal_subscribe() and g_dbus_connection_signal_unsubscribe() handled by the GIO GDBus API. - DBus object exporting is handled by g_dbus_connection_register_object(), using g_dbus_node_info_new_for_xml() to assist generating an interface table. - Exported method returns are now handled by g_dbus_method_invocation_return_value(). Similarly to g_dbus_method_invocation_return_error() and its variants. - BlueZ 5 has dropped the audio, input, moniter, and serial APIs in favor for the profile API. Because of this change bt-audio, bt-audio, bt-input, bt-moniter, and bt-serial have been removed from the project. Support for the profile API will be included in the future. - DiscoverServices has been removed in the BlueZ 5 device DBus API. Because of this, bt-device will use `sdptool' as a substitute for discovering services on remote devices. This will require bluez-utils to be installed. - OBEX is now a part of BlueZ 5. Because of this change, the option to compile bluez-tools without OBEX support has been removed. OBEX support will always be included in bluez-tools. -------------------------- bluez-tools-2.0~20170911.0.7cb788c/INSTALL000066400000000000000000000363321315563672100171500ustar00rootroot00000000000000Installation Instructions ************************* Copyright (C) 1994, 1995, 1996, 1999, 2000, 2001, 2002, 2004, 2005, 2006, 2007, 2008, 2009 Free Software Foundation, Inc. Copying and distribution of this file, with or without modification, are permitted in any medium without royalty provided the copyright notice and this notice are preserved. This file is offered as-is, without warranty of any kind. Basic Installation ================== Briefly, the shell commands `./configure; make; make install' should configure, build, and install this package. The following more-detailed instructions are generic; see the `README' file for instructions specific to this package. Some packages provide this `INSTALL' file but do not implement all of the features documented below. The lack of an optional feature in a given package is not necessarily a bug. More recommendations for GNU packages can be found in *note Makefile Conventions: (standards)Makefile Conventions. The `configure' shell script attempts to guess correct values for various system-dependent variables used during compilation. It uses those values to create a `Makefile' in each directory of the package. It may also create one or more `.h' files containing system-dependent definitions. Finally, it creates a shell script `config.status' that you can run in the future to recreate the current configuration, and a file `config.log' containing compiler output (useful mainly for debugging `configure'). It can also use an optional file (typically called `config.cache' and enabled with `--cache-file=config.cache' or simply `-C') that saves the results of its tests to speed up reconfiguring. Caching is disabled by default to prevent problems with accidental use of stale cache files. If you need to do unusual things to compile the package, please try to figure out how `configure' could check whether to do them, and mail diffs or instructions to the address given in the `README' so they can be considered for the next release. If you are using the cache, and at some point `config.cache' contains results you don't want to keep, you may remove or edit it. The file `configure.ac' (or `configure.in') is used to create `configure' by a program called `autoconf'. You need `configure.ac' if you want to change it or regenerate `configure' using a newer version of `autoconf'. The simplest way to compile this package is: 1. `cd' to the directory containing the package's source code and type `./configure' to configure the package for your system. Running `configure' might take a while. While running, it prints some messages telling which features it is checking for. 2. Type `make' to compile the package. 3. Optionally, type `make check' to run any self-tests that come with the package, generally using the just-built uninstalled binaries. 4. Type `make install' to install the programs and any data files and documentation. When installing into a prefix owned by root, it is recommended that the package be configured and built as a regular user, and only the `make install' phase executed with root privileges. 5. Optionally, type `make installcheck' to repeat any self-tests, but this time using the binaries in their final installed location. This target does not install anything. Running this target as a regular user, particularly if the prior `make install' required root privileges, verifies that the installation completed correctly. 6. You can remove the program binaries and object files from the source code directory by typing `make clean'. To also remove the files that `configure' created (so you can compile the package for a different kind of computer), type `make distclean'. There is also a `make maintainer-clean' target, but that is intended mainly for the package's developers. If you use it, you may have to get all sorts of other programs in order to regenerate files that came with the distribution. 7. Often, you can also type `make uninstall' to remove the installed files again. In practice, not all packages have tested that uninstallation works correctly, even though it is required by the GNU Coding Standards. 8. Some packages, particularly those that use Automake, provide `make distcheck', which can by used by developers to test that all other targets like `make install' and `make uninstall' work correctly. This target is generally not run by end users. Compilers and Options ===================== Some systems require unusual options for compilation or linking that the `configure' script does not know about. Run `./configure --help' for details on some of the pertinent environment variables. You can give `configure' initial values for configuration parameters by setting variables in the command line or in the environment. Here is an example: ./configure CC=c99 CFLAGS=-g LIBS=-lposix *Note Defining Variables::, for more details. Compiling For Multiple Architectures ==================================== You can compile the package for more than one kind of computer at the same time, by placing the object files for each architecture in their own directory. To do this, you can use GNU `make'. `cd' to the directory where you want the object files and executables to go and run the `configure' script. `configure' automatically checks for the source code in the directory that `configure' is in and in `..'. This is known as a "VPATH" build. With a non-GNU `make', it is safer to compile the package for one architecture at a time in the source code directory. After you have installed the package for one architecture, use `make distclean' before reconfiguring for another architecture. On MacOS X 10.5 and later systems, you can create libraries and executables that work on multiple system types--known as "fat" or "universal" binaries--by specifying multiple `-arch' options to the compiler but only a single `-arch' option to the preprocessor. Like this: ./configure CC="gcc -arch i386 -arch x86_64 -arch ppc -arch ppc64" \ CXX="g++ -arch i386 -arch x86_64 -arch ppc -arch ppc64" \ CPP="gcc -E" CXXCPP="g++ -E" This is not guaranteed to produce working output in all cases, you may have to build one architecture at a time and combine the results using the `lipo' tool if you have problems. Installation Names ================== By default, `make install' installs the package's commands under `/usr/local/bin', include files under `/usr/local/include', etc. You can specify an installation prefix other than `/usr/local' by giving `configure' the option `--prefix=PREFIX', where PREFIX must be an absolute file name. You can specify separate installation prefixes for architecture-specific files and architecture-independent files. If you pass the option `--exec-prefix=PREFIX' to `configure', the package uses PREFIX as the prefix for installing programs and libraries. Documentation and other data files still use the regular prefix. In addition, if you use an unusual directory layout you can give options like `--bindir=DIR' to specify different values for particular kinds of files. Run `configure --help' for a list of the directories you can set and what kinds of files go in them. In general, the default for these options is expressed in terms of `${prefix}', so that specifying just `--prefix' will affect all of the other directory specifications that were not explicitly provided. The most portable way to affect installation locations is to pass the correct locations to `configure'; however, many packages provide one or both of the following shortcuts of passing variable assignments to the `make install' command line to change installation locations without having to reconfigure or recompile. The first method involves providing an override variable for each affected directory. For example, `make install prefix=/alternate/directory' will choose an alternate location for all directory configuration variables that were expressed in terms of `${prefix}'. Any directories that were specified during `configure', but not in terms of `${prefix}', must each be overridden at install time for the entire installation to be relocated. The approach of makefile variable overrides for each directory variable is required by the GNU Coding Standards, and ideally causes no recompilation. However, some platforms have known limitations with the semantics of shared libraries that end up requiring recompilation when using this method, particularly noticeable in packages that use GNU Libtool. The second method involves providing the `DESTDIR' variable. For example, `make install DESTDIR=/alternate/directory' will prepend `/alternate/directory' before all installation names. The approach of `DESTDIR' overrides is not required by the GNU Coding Standards, and does not work on platforms that have drive letters. On the other hand, it does better at avoiding recompilation issues, and works well even when some directory options were not specified in terms of `${prefix}' at `configure' time. Optional Features ================= If the package supports it, you can cause programs to be installed with an extra prefix or suffix on their names by giving `configure' the option `--program-prefix=PREFIX' or `--program-suffix=SUFFIX'. Some packages pay attention to `--enable-FEATURE' options to `configure', where FEATURE indicates an optional part of the package. They may also pay attention to `--with-PACKAGE' options, where PACKAGE is something like `gnu-as' or `x' (for the X Window System). The `README' should mention any `--enable-' and `--with-' options that the package recognizes. For packages that use the X Window System, `configure' can usually find the X include and library files automatically, but if it doesn't, you can use the `configure' options `--x-includes=DIR' and `--x-libraries=DIR' to specify their locations. Some packages offer the ability to configure how verbose the execution of `make' will be. For these packages, running `./configure --enable-silent-rules' sets the default to minimal output, which can be overridden with `make V=1'; while running `./configure --disable-silent-rules' sets the default to verbose, which can be overridden with `make V=0'. Particular systems ================== On HP-UX, the default C compiler is not ANSI C compatible. If GNU CC is not installed, it is recommended to use the following options in order to use an ANSI C compiler: ./configure CC="cc -Ae -D_XOPEN_SOURCE=500" and if that doesn't work, install pre-built binaries of GCC for HP-UX. On OSF/1 a.k.a. Tru64, some versions of the default C compiler cannot parse its `' header file. The option `-nodtk' can be used as a workaround. If GNU CC is not installed, it is therefore recommended to try ./configure CC="cc" and if that doesn't work, try ./configure CC="cc -nodtk" On Solaris, don't put `/usr/ucb' early in your `PATH'. This directory contains several dysfunctional programs; working variants of these programs are available in `/usr/bin'. So, if you need `/usr/ucb' in your `PATH', put it _after_ `/usr/bin'. On Haiku, software installed for all users goes in `/boot/common', not `/usr/local'. It is recommended to use the following options: ./configure --prefix=/boot/common Specifying the System Type ========================== There may be some features `configure' cannot figure out automatically, but needs to determine by the type of machine the package will run on. Usually, assuming the package is built to be run on the _same_ architectures, `configure' can figure that out, but if it prints a message saying it cannot guess the machine type, give it the `--build=TYPE' option. TYPE can either be a short name for the system type, such as `sun4', or a canonical name which has the form: CPU-COMPANY-SYSTEM where SYSTEM can have one of these forms: OS KERNEL-OS See the file `config.sub' for the possible values of each field. If `config.sub' isn't included in this package, then this package doesn't need to know the machine type. If you are _building_ compiler tools for cross-compiling, you should use the option `--target=TYPE' to select the type of system they will produce code for. If you want to _use_ a cross compiler, that generates code for a platform different from the build platform, you should specify the "host" platform (i.e., that on which the generated programs will eventually be run) with `--host=TYPE'. Sharing Defaults ================ If you want to set default values for `configure' scripts to share, you can create a site shell script called `config.site' that gives default values for variables like `CC', `cache_file', and `prefix'. `configure' looks for `PREFIX/share/config.site' if it exists, then `PREFIX/etc/config.site' if it exists. Or, you can set the `CONFIG_SITE' environment variable to the location of the site script. A warning: not all `configure' scripts look for a site script. Defining Variables ================== Variables not defined in a site shell script can be set in the environment passed to `configure'. However, some packages may run configure again during the build, and the customized values of these variables may be lost. In order to avoid this problem, you should set them in the `configure' command line, using `VAR=value'. For example: ./configure CC=/usr/local2/bin/gcc causes the specified `gcc' to be used as the C compiler (unless it is overridden in the site shell script). Unfortunately, this technique does not work for `CONFIG_SHELL' due to an Autoconf bug. Until the bug is fixed you can use this workaround: CONFIG_SHELL=/bin/bash /bin/bash ./configure CONFIG_SHELL=/bin/bash `configure' Invocation ====================== `configure' recognizes the following options to control how it operates. `--help' `-h' Print a summary of all of the options to `configure', and exit. `--help=short' `--help=recursive' Print a summary of the options unique to this package's `configure', and exit. The `short' variant lists options used only in the top level, while the `recursive' variant lists options also present in any nested packages. `--version' `-V' Print the version of Autoconf used to generate the `configure' script, and exit. `--cache-file=FILE' Enable the cache: use and save the results of the tests in FILE, traditionally `config.cache'. FILE defaults to `/dev/null' to disable caching. `--config-cache' `-C' Alias for `--cache-file=config.cache'. `--quiet' `--silent' `-q' Do not print messages saying which checks are being made. To suppress all normal output, redirect it to `/dev/null' (any error messages will still be shown). `--srcdir=DIR' Look for the package's source code in directory DIR. Usually `configure' can determine that directory automatically. `--prefix=DIR' Use DIR as the installation prefix. *note Installation Names:: for more details, including other options available for fine-tuning the installation locations. `--no-create' `-n' Run the configure checks, but stop before creating any output files. `configure' also accepts some other, not widely useful, options. Run `configure --help' for more details. bluez-tools-2.0~20170911.0.7cb788c/Makefile.am000066400000000000000000000003631315563672100201460ustar00rootroot00000000000000BUILT_SOURCES = $(top_srcdir)/.version $(top_srcdir)/.version: echo $(VERSION) > $@-t && mv $@-t $@ dist-hook: echo $(VERSION) > $(distdir)/.tarball-version CLEANFILES = $(top_srcdir)/.version SUBDIRS = src EXTRA_DIST = git-version-gen bluez-tools-2.0~20170911.0.7cb788c/NEWS000066400000000000000000000000001315563672100165750ustar00rootroot00000000000000bluez-tools-2.0~20170911.0.7cb788c/README000066400000000000000000000077261315563672100170040ustar00rootroot00000000000000bluez-tools =========== See "Installation" for compile instructions. This was a GSoC'10 project to implement a new command line tools for bluez (bluetooth stack for linux). It is currently an active open source project. The project is implemented in C and uses the D-Bus interface of bluez. The project is still a work in progress, and not all APIs from Bluez have been implemented as a part of bluez-tools. The APIs which have been implemented in bluez-tools are adapter, agent, device, network and obex. Other APIs, such as interfaces for medical devices, pedometers and other specific APIs have not been ported to bluez-tools. Some bluez-tool source relied on the previous version of bluez (4), and have been deprecated, dropped and removed from the code. If such functionality exists in another form in bluez (5), a developer should feel free to clone the project, make the changes and send a merge request. If this is a major change, perhaps requiring multiple eyes, a developer should consider registering a change request at the project git repository. We support the project and welcome changes :) The project is currently a beta version, and hiccups will still be present in the code. Register bugs at the project git repository. Project website: http://code.google.com/p/bluez-tools/ Project Git repository: https://github.com/khvzak/bluez-tools bt-adapter ========== - List available adapters - Show information about adapter (incl properties) - Discover remote devices (with remote device name resolving) - Change adapter properties (eg. Name, Discoverable, Pairable, etc) bt-agent ======== - Manage incoming Bluetooth requests (eg. request of pincode, request of authorize a connection/service request, etc) bt-device ========= - List added devices - Connect to the remote device by his MAC, retrieve all SDP records and then initiate the pairing - Disconnect the remote device - Remove device (and also the pairing information) - Show information about device (incl properties) - Service discovery - Change device properties (eg. Name, Trusted, Blocked, etc) bt-network ========== - Connect to the network device - Register network server for the provided UUID (gn/panu/nap) bt-obex ======= - Agent (to accept/reject incoming bluetooth object push requests) for OBEXD (OPP/FTP profile) - Send local file to the specified remote device using object push profile - Start FTP session with remote device Installation ============ Run `./autogen.sh' at the project root directory. This will generate the missing files you need to compile. Then run `./configure' followed by `make' and then `make install' to compile and install bluez-tools. `make install' requires root access. You can read `INSTALL' for detailed instructions on how to use `./configure'. Requirements ============ bluez-tools post v0.2 uses bluez-5.20 API. Due to the removal of DiscoverServices in the BlueZ 5 device API, bt-device requires `sdptool' (included in bluez-utils) for service discovery. Release Notes ============ For information regarding the changes of bluez-tools, please refer to the `ChangeLog' file included in the project. License ============ bluez-tools is released under the GNU General Public License version 2 (GPLv2). Refer to the `COPYING' file for details regarding the license. Known Issues ============ - Discovery mode on `bt-adapter' has no default timeout, which means it will last indefinitly. Using SIGINT (control-c) turns off the discovery scan and exits `bt-adapter'. - `bt-agent' does not recieve a `unregistered' callback signal in BlueZ 5, even when the agent manager successfully unregisters the agent. You will need to use SIGINT (control-c) twice to exit `bt-agent'. - Running `bt-agent' as a daemon process is currently broken.' - bt-network and bt-obex FTP has been implemented but it is largely untested with BlueZ 5. Unaddressed Issues From Pre v0.2 ============ - FTP session closes unexpectedly after the command "ls" (bug in OBEXD?) - Copy/Move methods not yet implemented (OBEXD) bluez-tools-2.0~20170911.0.7cb788c/autogen.sh000077500000000000000000000001031315563672100201030ustar00rootroot00000000000000#!/bin/sh autoreconf --force --install --verbose ./configure "$@" bluez-tools-2.0~20170911.0.7cb788c/configure.ac000066400000000000000000000035061315563672100204020ustar00rootroot00000000000000AC_INIT([bluez-tools], m4_esyscmd([./git-version-gen .tarball-version]), [zxteam@gmail.com], [bluez-tools], [http://code.google.com/p/bluez-tools/]) AC_PREREQ([2.65]) AM_INIT_AUTOMAKE([1.11 no-define foreign -Wall subdir-objects]) AC_CONFIG_HEADERS([config.h]) # The default CFLAGS and CXXFLAGS in Autoconf are "-g -O2" for gcc and just # "-g" for any other compiler. There doesn't seem to be a standard way of # getting rid of the -g (which I don't think is needed for a production # library). This fudge seems to achieve the necessary. First, we remember the # externally set values of CFLAGS and CXXFLAGS. Then call the AC_PROG_CC and # AC_PROG_CXX macros to find the compilers - if CFLAGS and CXXFLAGS are not # set, they will be set to Autoconf's defaults. Afterwards, if the original # values were not set, remove the -g from the Autoconf defaults. # (PH 02-May-07) remember_set_CFLAGS="$CFLAGS" AC_PROG_CC AC_PROG_CC_C99 if test "x$remember_set_CFLAGS" = "x" then if test "$CFLAGS" = "-g -O2" then CFLAGS="-O2" elif test "$CFLAGS" = "-g" then CFLAGS="" fi fi AC_PROG_INSTALL AM_PROG_CC_C_O # Checks for header files. AC_HEADER_STDC # Check for the availability of dbus and glib libs PKG_PROG_PKG_CONFIG PKG_CHECK_MODULES([GLIB], [glib-2.0 >= 2.36.0]) PKG_CHECK_MODULES([GIO], [gio-2.0 >= 2.26.0 gio-unix-2.0 >= 2.26.0]) # Check for the availability of libreadline AC_CHECK_HEADERS([readline/readline.h], [HAVE_READLINE_H=1]) AC_CHECK_HEADERS([readline/history.h], [HAVE_HISTORY_H=1]) AC_CHECK_LIB([readline], [readline], [HAVE_LIB_READLINE=1]) if test "$HAVE_READLINE_H" != "1"; then echo "** readline/readline.h was not found." exit 1 fi if test "$HAVE_HISTORY_H" != "1"; then echo "** readline/history.h was not found." exit 1 fi LIBREADLINE="-lreadline" AC_SUBST(LIBREADLINE) AC_CONFIG_FILES([Makefile src/Makefile]) AC_OUTPUT bluez-tools-2.0~20170911.0.7cb788c/contrib/000077500000000000000000000000001315563672100175505ustar00rootroot00000000000000bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/000077500000000000000000000000001315563672100231175ustar00rootroot00000000000000bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/adapter-api.txt000066400000000000000000000103441315563672100260510ustar00rootroot00000000000000BlueZ D-Bus Adapter API description *********************************** Adapter hierarchy ================= Service org.bluez Interface org.bluez.Adapter1 Object path [variable prefix]/{hci0,hci1,...} Methods void StartDiscovery() This method starts the device discovery session. This includes an inquiry procedure and remote device name resolving. Use StopDiscovery to release the sessions acquired. This process will start creating Device objects as new devices are discovered. Possible errors: org.bluez.Error.NotReady org.bluez.Error.Failed void StopDiscovery() This method will cancel any previous StartDiscovery transaction. Note that a discovery procedure is shared between all discovery sessions thus calling StopDiscovery will only release a single session. Possible errors: org.bluez.Error.NotReady org.bluez.Error.Failed org.bluez.Error.NotAuthorized void RemoveDevice(object device) This removes the remote device object at the given path. It will remove also the pairing information. Possible errors: org.bluez.Error.InvalidArguments org.bluez.Error.Failed Properties string Address [readonly] The Bluetooth device address. string Name [readonly] The Bluetooth system name (pretty hostname). This property is either a static system default or controlled by an external daemon providing access to the pretty hostname configuration. string Alias [readwrite] The Bluetooth friendly name. This value can be changed. In case no alias is set, it will return the system provided name. Setting an empty string as alias will convert it back to the system provided name. When resetting the alias with an empty string, the property will default back to system name. On a well configured system, this property never needs to be changed since it defaults to the system name and provides the pretty hostname. Only if the local name needs to be different from the pretty hostname, this property should be used as last resort. uint32 Class [readonly] The Bluetooth class of device. This property represents the value that is either automatically configured by DMI/ACPI information or provided as static configuration. boolean Powered [readwrite] Switch an adapter on or off. This will also set the appropriate connectable state of the controller. The value of this property is not persistent. After restart or unplugging of the adapter it will reset back to false. boolean Discoverable [readwrite] Switch an adapter to discoverable or non-discoverable to either make it visible or hide it. This is a global setting and should only be used by the settings application. If the DiscoverableTimeout is set to a non-zero value then the system will set this value back to false after the timer expired. In case the adapter is switched off, setting this value will fail. When changing the Powered property the new state of this property will be updated via a PropertyChanged signal. For any new adapter this settings defaults to false. boolean Pairable [readwrite] Switch an adapter to pairable or non-pairable. This is a global setting and should only be used by the settings application. Note that this property only affects incoming pairing requests. For any new adapter this settings defaults to true. uint32 PairableTimeout [readwrite] The pairable timeout in seconds. A value of zero means that the timeout is disabled and it will stay in pairable mode forever. The default value for pairable timeout should be disabled (value 0). uint32 DiscoverableTimeout [readwrite] The discoverable timeout in seconds. A value of zero means that the timeout is disabled and it will stay in discoverable/limited mode forever. The default value for the discoverable timeout should be 180 seconds (3 minutes). boolean Discovering [readonly] Indicates that a device discovery procedure is active. array{string} UUIDs [readonly] List of 128-bit UUIDs that represents the available local services. string Modalias [readonly, optional] Local Device ID information in modalias format used by the kernel and udev. bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/agent-api.txt000066400000000000000000000125721315563672100255340ustar00rootroot00000000000000BlueZ D-Bus Agent API description ********************************** Agent Manager hierarchy ======================= Service org.bluez Interface org.bluez.AgentManager1 Object path /org/bluez Methods void RegisterAgent(object agent, string capability) This registers an agent handler. The object path defines the path of the agent that will be called when user input is needed. Every application can register its own agent and for all actions triggered by that application its agent is used. It is not required by an application to register an agent. If an application does chooses to not register an agent, the default agent is used. This is on most cases a good idea. Only application like a pairing wizard should register their own agent. An application can only register one agent. Multiple agents per application is not supported. The capability parameter can have the values "DisplayOnly", "DisplayYesNo", "KeyboardOnly", "NoInputNoOutput" and "KeyboardDisplay" which reflects the input and output capabilities of the agent. If an empty string is used it will fallback to "DisplayYesNo". Possible errors: org.bluez.Error.InvalidArguments org.bluez.Error.AlreadyExists void UnregisterAgent(object agent) This unregisters the agent that has been previously registered. The object path parameter must match the same value that has been used on registration. Possible errors: org.bluez.Error.DoesNotExist void RequestDefaultAgent(object agent) This requests is to make the application agent the default agent. The application is required to register an agent. Special permission might be required to become the default agent. Possible errors: org.bluez.Error.DoesNotExist Agent hierarchy =============== Service unique name Interface org.bluez.Agent1 Object path freely definable Methods void Release() This method gets called when the service daemon unregisters the agent. An agent can use it to do cleanup tasks. There is no need to unregister the agent, because when this method gets called it has already been unregistered. string RequestPinCode(object device) This method gets called when the service daemon needs to get the passkey for an authentication. The return value should be a string of 1-16 characters length. The string can be alphanumeric. Possible errors: org.bluez.Error.Rejected org.bluez.Error.Canceled void DisplayPinCode(object device, string pincode) This method gets called when the service daemon needs to display a pincode for an authentication. An empty reply should be returned. When the pincode needs no longer to be displayed, the Cancel method of the agent will be called. This is used during the pairing process of keyboards that don't support Bluetooth 2.1 Secure Simple Pairing, in contrast to DisplayPasskey which is used for those that do. This method will only ever be called once since older keyboards do not support typing notification. Note that the PIN will always be a 6-digit number, zero-padded to 6 digits. This is for harmony with the later specification. Possible errors: org.bluez.Error.Rejected org.bluez.Error.Canceled uint32 RequestPasskey(object device) This method gets called when the service daemon needs to get the passkey for an authentication. The return value should be a numeric value between 0-999999. Possible errors: org.bluez.Error.Rejected org.bluez.Error.Canceled void DisplayPasskey(object device, uint32 passkey, uint16 entered) This method gets called when the service daemon needs to display a passkey for an authentication. The entered parameter indicates the number of already typed keys on the remote side. An empty reply should be returned. When the passkey needs no longer to be displayed, the Cancel method of the agent will be called. During the pairing process this method might be called multiple times to update the entered value. Note that the passkey will always be a 6-digit number, so the display should be zero-padded at the start if the value contains less than 6 digits. void RequestConfirmation(object device, uint32 passkey) This method gets called when the service daemon needs to confirm a passkey for an authentication. To confirm the value it should return an empty reply or an error in case the passkey is invalid. Note that the passkey will always be a 6-digit number, so the display should be zero-padded at the start if the value contains less than 6 digits. Possible errors: org.bluez.Error.Rejected org.bluez.Error.Canceled void RequestAuthorization(object device) This method gets called to request the user to authorize an incoming pairing attempt which would in other circumstances trigger the just-works model. Possible errors: org.bluez.Error.Rejected org.bluez.Error.Canceled void AuthorizeService(object device, string uuid) This method gets called when the service daemon needs to authorize a connection/service request. Possible errors: org.bluez.Error.Rejected org.bluez.Error.Canceled void Cancel() This method gets called to indicate that the agent request failed before a reply was returned. bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/agent.xml000066400000000000000000000022711315563672100247410ustar00rootroot00000000000000 bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/alert-api.txt000066400000000000000000000067331315563672100255470ustar00rootroot00000000000000BlueZ D-Bus Alert API description ********************************* Introduction ------------ Currently, there are two different GATT server profiles that depend on receiving alerts or notifications from the platform: Phone Alert Status (PASP) and Alert Notification (ANP). PASP is very specific to mobile phones, and also allows limited control to alerts (i.e. mute once or switch to a silent mode). This document presents a unified API that allows to register and notify alerts, and to control some alerts (using the provided agent object). Alert hierarchy =============== Service org.bluez Interface org.bluez.Alert1 Object path /org/bluez Methods void RegisterAlert(string category, object agent) Register a new alert category and an agent for it. This means the application will be responsible for notifying BlueZ of any alerts of that category, using the NewAlert() method. Supported ANP categories: simple, email, news, call, missed-call, sms-mms, voice-mail, schedule, high-priority, instant-message Supported PASP categories: ringer, vibrate, display Possible Errors: org.bluez.Error.InvalidArguments void NewAlert(string category, uint16 count, string description) Notify BlueZ of new alert(s) for the given category. The description is relative to the last received alert and can be sender name, caller ID, title, or other information specific to the category. For ringer, vibrate and display categories, valid descriptions are "active" and "not active". Alerts from ringer category also accept "enabled" and "disabled", depending on whether ringer is in silent mode or not. Description must not exceed 18 bytes when encoded in UTF-8 format, otherwise an error is returned. If there is no description, an empty string should be used. The count argument contains the number of alerts not yet acknowledged by the user on the UI. To save D-Bus traffic, events that may generate multiple alerts at the same time (like email, sms, news) should trigger a single NewAlert(). If there are more than 254 new alerts, count must be set to 255. PASP alerts should always set count to 1. Possible Errors: org.bluez.Error.InvalidArguments void UnreadAlert(string category, uint16 count) Some services (like SMS and e-mail) keep track of number of unread items. This method allows to update this counter, so peer devices can be notified using Alert Notification Profile. If there are more than 254 unread alerts, count must be set to 255. Possible Errors: org.bluez.Error.InvalidArguments Alert Agent hierarchy ===================== Service org.bluez Interface org.bluez.AlertAgent1 Object path freely definable Methods void MuteOnce() This method is only called if "ringer" alert category is specified when registering the agent. Mute the ringer once (e.g. during a incoming call). If ringer is not active, does nothing. void SetRinger(string mode) This method is only called if "ringer" alert category is specified when registering the agent. Set ringer to the specified mode. If mode is "enabled", ringer is set to the default mode, as defined by the current active profile. If mode is "disabled", ringer will not activate on incoming calls, until it is set back to "enabled" mode. Possible Errors: org.bluez.Error.InvalidArguments void Release() Release this agent. At this point, it will not be used by BlueZ anymore and can be destroyed by the owner. bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/assigned-numbers.txt000066400000000000000000000006261315563672100271320ustar00rootroot00000000000000RFCOMM Channels =============== Since there are a limited amount of possible RFCOMM channels (1-31) they've been pre-allocated for currently known profiles in order to avoid conflicts. Profile Channel ----------------------- DUN 1 HFP HF 7 OPP 9 FTP 10 BIP 11 HSP AG 12 HFP AG 13 SYNCH (IrMC) 14 PBAP 15 MAP MAS 16 MAP MNS 17 SyncEvolution 19 PC/Ovi Suite 24 SyncML Client 25 SyncML Server 26 bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/cyclingspeed-api.txt000066400000000000000000000053521315563672100271050ustar00rootroot00000000000000Cycling Speed and Cadence API description ***************************************** Cycling Speed and Cadence Manager hierarchy =========================================== Service org.bluez Interface org.bluez.CyclingSpeedManager1 Object path [variable prefix]/{hci0,hci1,...} Methods RegisterWatcher(object agent) Registers a watcher to monitor cycling speed and cadence measurements. Possible Errors: org.bluez.Error.InvalidArguments UnregisterWatcher(object agent) Unregisters a watcher. Cycling Speed and Cadence Profile hierarchy =========================================== Service org.bluez Interface org.bluez.CyclingSpeed1 Object path [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX Methods SetCumulativeWheelRevolutions(uint32 value) Sets cumulative wheel revolutions value if Cumulative Wheel Revolutions feature is supported. Possible Errors: org.bluez.Error.NotSupported Properties string Location (optional) [readwrite] Current sensor location, if supported. If Multiple Sensor Locations feature is supported, this property can be set to one of values read from SupportedLocations property. Possible values: "other", "top-of-shoe", "in-shoe", "hip", "front-wheel", "left-crank", "right-crank", "left-pedal", "right-pedal", "front-hub", "rear-dropout", "chainstay", "rear-wheel", "rear-hub" array{string} SupportedLocations (optional) [readonly] List of locations supported by sensor, only present if Multiple Sensor Locations feature is supported. boolean WheelRevolutionDataSupported [readonly] true if sensor can read and set Cumulative Wheel Revolutions value, false otherwise. boolean MultipleLocationsSupported [readonly] true if sensor supports Multiple Sensor Locations feature and can set Location, false otherwise. Cycling Speed and Cadence Watcher hierarchy =========================================== Service unique name Interface org.bluez.CyclingSpeedWatcher1 Object path freely definable Methods void MeasurementReceived(object device, dict measurement) This callback is called whenever wheel and/or crank revolutions measurement is received from sensor. Measurement: uint32 WheelRevolutions (optional): Cumulative number of wheel revolutions. uint16 LastWheelEventTime (optional): Time of last event from wheel sensor. Value is expressed in 1/1024 second units and can roll over during a ride. uint16 CrankRevolutions (optional): Cumulative number of crank revolutions. This value can occasionally roll over. uint16 LastCrankEventTime (optional): Time of last event from crank sensor. Value is expressed in 1/1024 second units and can roll over during a ride. bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/device-api.txt000066400000000000000000000130211315563672100256630ustar00rootroot00000000000000BlueZ D-Bus Device API description ********************************** Device hierarchy ================ Service org.bluez Interface org.bluez.Device1 Object path [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX Methods void Connect() This is a generic method to connect any profiles the remote device supports that can be connected to and have been flagged as auto-connectable on our side. If only subset of profiles is already connected it will try to connect currently disconnected ones. If at least one profile was connected successfully this method will indicate success. Possible errors: org.bluez.Error.NotReady org.bluez.Error.Failed org.bluez.Error.InProgress org.bluez.Error.AlreadyConnected void Disconnect() This method gracefully disconnects all connected profiles and then terminates low-level ACL connection. ACL connection will be terminated even if some profiles were not disconnected properly e.g. due to misbehaving device. This method can be also used to cancel a preceding Connect call before a reply to it has been received. Possible errors: org.bluez.Error.NotConnected void ConnectProfile(string uuid) This method connects a specific profile of this device. The UUID provided is the remote service UUID for the profile. Possible errors: org.bluez.Error.DoesNotExist org.bluez.Error.AlreadyConnected org.bluez.Error.ConnectFailed void DisconnectProfile(string uuid) This method disconnects a specific profile of this device. The profile needs to be registered client profile. There is no connection tracking for a profile, so as long as the profile is registered this will always succeed. Possible errors: org.bluez.Error.DoesNotExist org.bluez.Error.Failed org.bluez.Error.NotConnected org.bluez.Error.NotSupported void Pair() This method will connect to the remote device, initiate pairing and then retrieve all SDP records (or GATT primary services). If the application has registered its own agent, then that specific agent will be used. Otherwise it will use the default agent. Only for applications like a pairing wizard it would make sense to have its own agent. In almost all other cases the default agent will handle this just fine. In case there is no application agent and also no default agent present, this method will fail. Possible errors: org.bluez.Error.InvalidArguments org.bluez.Error.Failed org.bluez.Error.AlreadyExists org.bluez.Error.AuthenticationCanceled org.bluez.Error.AuthenticationFailed org.bluez.Error.AuthenticationRejected org.bluez.Error.AuthenticationTimeout org.bluez.Error.ConnectionAttemptFailed void CancelPairing() This method can be used to cancel a pairing operation initiated by the Pair method. Possible errors: org.bluez.Error.DoesNotExist org.bluez.Error.Failed Properties string Address [readonly] The Bluetooth device address of the remote device. string Name [readonly, optional] The Bluetooth remote name. This value can not be changed. Use the Alias property instead. This value is only present for completeness. It is better to always use the Alias property when displaying the devices name. If the Alias property is unset, it will reflect this value which makes it more convenient. string Icon [readonly, optional] Proposed icon name according to the freedesktop.org icon naming specification. uint32 Class [readonly, optional] The Bluetooth class of device of the remote device. uint16 Appearance [readonly, optional] External appearance of device, as found on GAP service. array{string} UUIDs [readonly, optional] List of 128-bit UUIDs that represents the available remote services. boolean Paired [readonly] Indicates if the remote device is paired. boolean Connected [readonly] Indicates if the remote device is currently connected. A PropertiesChanged signal indicate changes to this status. boolean Trusted [readwrite] Indicates if the remote is seen as trusted. This setting can be changed by the application. boolean Blocked [readwrite] If set to true any incoming connections from the device will be immediately rejected. Any device drivers will also be removed and no new ones will be probed as long as the device is blocked. string Alias [readwrite] The name alias for the remote device. The alias can be used to have a different friendly name for the remote device. In case no alias is set, it will return the remote device name. Setting an empty string as alias will convert it back to the remote device name. When resetting the alias with an empty string, the property will default back to the remote name. object Adapter [readonly] The object path of the adapter the device belongs to. boolean LegacyPairing [readonly] Set to true if the device only supports the pre-2.1 pairing mechanism. This property is useful in the Adapter.DeviceFound signal to anticipate whether legacy or simple pairing will occur. Note that this property can exhibit false-positives in the case of Bluetooth 2.1 (or newer) devices that have disabled Extended Inquiry Response support. string Modalias [readonly, optional] Remote Device ID information in modalias format used by the kernel and udev. int16 RSSI [readonly, optional] Received Signal Strength Indicator of the remote device (inquiry or advertising). bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/health-api.txt000066400000000000000000000076451315563672100257100ustar00rootroot00000000000000BlueZ D-Bus Health API description ********************************** HealthManager hierarchy ======================= Service org.bluez Interface org.bluez.HealthManager1 Object path /org/bluez/ Methods object CreateApplication(dict config) Returns the path of the new registered application. Application will be closed by the call or implicitly when the programs leaves the bus. config: uint16 DataType: Mandatory string Role: Mandatory. Possible values: "source", "sink" string Description: Optional ChannelType: Optional, just for sources. Possible values: "reliable", "streaming" Possible Errors: org.bluez.Error.InvalidArguments void DestroyApplication(object application) Closes the HDP application identified by the object path. Also application will be closed if the process that started it leaves the bus. Only the creator of the application will be able to destroy it. Possible errors: org.bluez.Error.InvalidArguments org.bluez.Error.NotFound org.bluez.Error.NotAllowed HealthDevice hierarchy ====================== Service org.bluez Interface org.bluez.HealthDevice1 Object path [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX Methods boolean Echo() Sends an echo petition to the remote service. Returns True if response matches with the buffer sent. If some error is detected False value is returned. Possible errors: org.bluez.Error.InvalidArguments org.bluez.Error.OutOfRange object CreateChannel(object application, string configuration) Creates a new data channel. The configuration should indicate the channel quality of service using one of this values "reliable", "streaming", "any". Returns the object path that identifies the data channel that is already connected. Possible errors: org.bluez.Error.InvalidArguments org.bluez.Error.HealthError void DestroyChannel(object channel) Destroys the data channel object. Only the creator of the channel or the creator of the HealthApplication that received the data channel will be able to destroy it. Possible errors: org.bluez.Error.InvalidArguments org.bluez.Error.NotFound org.bluez.Error.NotAllowed Signals void ChannelConnected(object channel) This signal is launched when a new data channel is created or when a known data channel is reconnected. void ChannelDeleted(object channel) This signal is launched when a data channel is deleted. After this signal the data channel path will not be valid and its path can be reused for future data channels. Properties object MainChannel [readonly] The first reliable channel opened. It is needed by upper applications in order to send specific protocol data units. The first reliable can change after a reconnection. HealthChannel hierarchy ======================= Service org.bluez Interface org.bluez.HealthChannel1 Object path [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX/chanZZZ Only the process that created the data channel or the creator of the HealthApplication that received it will be able to call these methods. Methods fd Acquire() Returns the file descriptor for this data channel. If the data channel is not connected it will also reconnect. Possible Errors: org.bluez.Error.NotConnected org.bluez.Error.NotAllowed void Release() Releases the fd. Application should also need to close() it. Possible Errors: org.bluez.Error.NotAcquired org.bluez.Error.NotAllowed Properties string Type [readonly] The quality of service of the data channel. ("reliable" or "streaming") object Device [readonly] Identifies the Remote Device that is connected with. Maps with a HealthDevice object. object Application [readonly] Identifies the HealthApplication to which this channel is related to (which indirectly defines its role and data type). bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/heartrate-api.txt000066400000000000000000000033461315563672100264140ustar00rootroot00000000000000Heart Rate API description ************************** Heart Rate Manager hierarchy ============================ Service org.bluez Interface org.bluez.HeartRateManager1 Object path [variable prefix]/{hci0,hci1,...} Methods RegisterWatcher(object agent) Registers a watcher to monitor heart rate measurements. Possible Errors: org.bluez.Error.InvalidArguments UnregisterWatcher(object agent) Unregisters a watcher. Heart Rate Profile hierarchy ============================ Service org.bluez Interface org.bluez.HeartRate1 Object path [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX Methods Reset() Restart the accumulation of energy expended from zero. Possible Errors: org.bluez.Error.NotSupported Properties string Location (optional) [readonly] Possible values: "other", "chest", "wrist","winger", "hand", "earlobe", "foot" boolean ResetSupported [readonly] True if energy expended is supported. Heart Rate Watcher hierarchy ============================ Service unique name Interface org.bluez.HeartRateWatcher1 Object path freely definable Methods void MeasurementReceived(object device, dict measurement) This callback is called whenever a heart rate measurement is received from the heart rate device. Measurement: uint16 Value: Measurement value expressed in beats per minute (bpm) uint16 Energy (optional): Accumulated energy expended in kilo Joules boolean Contact (optional): true if skin contact is detected by sensor, false otherwise array{uint16} Interval (optional): RR-Interval values which represent the time between two consecutive R waves in an ECG. Values are ordered starting from oldest to most recent. bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/media-api.txt000066400000000000000000000331471315563672100255160ustar00rootroot00000000000000BlueZ D-Bus Media API description ********************************* Media hierarchy =============== Service org.bluez Interface org.bluez.Media1 Object path [variable prefix]/{hci0,hci1,...} Methods void RegisterEndpoint(object endpoint, dict properties) Register a local end point to sender, the sender can register as many end points as it likes. Note: If the sender disconnects the end points are automatically unregistered. possible properties: string UUID: UUID of the profile which the endpoint is for. byte Codec: Assigned number of codec that the endpoint implements. The values should match the profile specification which is indicated by the UUID. array{byte} Capabilities: Capabilities blob, it is used as it is so the size and byte order must match. Possible Errors: org.bluez.Error.InvalidArguments org.bluez.Error.NotSupported - emitted when interface for the end-point is disabled. void UnregisterEndpoint(object endpoint) Unregister sender end point. void RegisterPlayer(object player, dict properties) Register a media player object to sender, the sender can register as many objects as it likes. Object must implement at least org.mpris.MediaPlayer2.Player as defined in MPRIS 2.2 spec: http://specifications.freedesktop.org/mpris-spec/latest/ Note: If the sender disconnects its objects are automatically unregistered. Possible Errors: org.bluez.Error.InvalidArguments org.bluez.Error.NotSupported void UnregisterPlayer(object player) Unregister sender media player. Media Control hierarchy ======================= Service org.bluez Interface org.bluez.MediaControl1 [Deprecated] Object path [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX Methods void Play() Resume playback. void Pause() Pause playback. void Stop() Stop playback. void Next() Next item. void Previous() Previous item. void VolumeUp() Adjust remote volume one step up void VolumeDown() Adjust remote volume one step down void FastForward() Fast forward playback, this action is only stopped when another method in this interface is called. void Rewind() Rewind playback, this action is only stopped when another method in this interface is called. Properties boolean Connected [readonly] MediaPlayer1 hierarchy ====================== Service org.bluez (Controller role) Interface org.bluez.MediaPlayer1 [Experimental] Object path [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX/playerX Methods void Play() Resume playback. Possible Errors: org.bluez.Error.NotSupported org.bluez.Error.Failed void Pause() Pause playback. Possible Errors: org.bluez.Error.NotSupported org.bluez.Error.Failed void Stop() Stop playback. Possible Errors: org.bluez.Error.NotSupported org.bluez.Error.Failed void Next() Next item. Possible Errors: org.bluez.Error.NotSupported org.bluez.Error.Failed void Previous() Previous item. Possible Errors: org.bluez.Error.NotSupported org.bluez.Error.Failed void FastForward() Fast forward playback, this action is only stopped when another method in this interface is called. Possible Errors: org.bluez.Error.NotSupported org.bluez.Error.Failed void Rewind() Rewind playback, this action is only stopped when another method in this interface is called. Possible Errors: org.bluez.Error.NotSupported org.bluez.Error.Failed Properties string Equalizer [readwrite] Possible values: "off" or "on" string Repeat [readwrite] Possible values: "off", "singletrack", "alltracks" or "group" string Shuffle [readwrite] Possible values: "off", "alltracks" or "group" string Scan [readwrite] Possible values: "off", "alltracks" or "group" string Status [readonly] Possible status: "playing", "stopped", "paused", "forward-seek", "reverse-seek" or "error" uint32 Position [readonly] Playback position in milliseconds. Changing the position may generate additional events that will be sent to the remote device. When position is 0 it means the track is starting and when it's greater than or equal to track's duration the track has ended. Note that even if duration is not available in metadata it's possible to signal its end by setting position to the maximum uint32 value. dict Track [readonly] Track metadata. Possible values: string Title: Track title name string Artist: Track artist name string Album: Track album name string Genre: Track genre name uint32 NumberOfTracks: Number of tracks in total uint32 TrackNumber: Track number uint32 Duration: Track duration in milliseconds object Device [readonly] Device object path. string Name [readonly] Player name string Type [readonly] Player type Possible values: "Audio" "Video" "Audio Broadcasting" "Video Broadcasting" string Subtype [readonly] Player subtype Possible values: "Audio Book" "Podcast" boolean Browsable [readonly] If present indicates the player can be browsed using MediaFolder interface. Possible values: True: Supported and active False: Supported but inactive Note: If supported but inactive clients can enable it by using MediaFolder interface but it might interfere in the playback of other players. boolean Searchable [readonly] If present indicates the player can be searched using MediaFolder interface. Possible values: True: Supported and active False: Supported but inactive Note: If supported but inactive clients can enable it by using MediaFolder interface but it might interfere in the playback of other players. object Playlist Playlist object path. MediaFolder1 hierarchy ====================== Service unique name (Target role) org.bluez (Controller role) Interface org.bluez.MediaFolder1 [Experimental] Object path freely definable (Target role) [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX/playerX (Controller role) Methods object Search(string value, dict filter) Return a folder object containing the search result. To list the items found use the folder object returned and pass to ChangeFolder. Possible Errors: org.bluez.Error.NotSupported org.bluez.Error.Failed array{objects, properties} ListItems(dict filter) Return a list of items found Possible Errors: org.bluez.Error.InvalidArguments org.bluez.Error.NotSupported org.bluez.Error.Failed void ChangeFolder(object folder) Change current folder. Note: By changing folder the items of previous folder might be destroyed and have to be listed again, the exception is NowPlaying folder which should be always present while the player is active. Possible Errors: org.bluez.Error.InvalidArguments org.bluez.Error.NotSupported org.bluez.Error.Failed Properties uint32 NumberOfItems [readonly] Number of items in the folder string Name [readonly] Folder name: Possible values: "/Filesystem/...": Filesystem scope "/NowPlaying/...": NowPlaying scope Note: /NowPlaying folder might not be listed if player is stopped, folders created by Search are virtual so once another Search is perform or the folder is changed using ChangeFolder it will no longer be listed. Filters uint32 Start: Offset of the first item. Default value: 0 uint32 End: Offset of the last item. Default value: NumbeOfItems array{string} Attributes Item properties that should be included in the list. Possible Values: "title", "artist", "album", "genre", "number-of-tracks", "number", "duration" Default Value: All MediaItem1 hierarchy ==================== Service unique name (Target role) org.bluez (Controller role) Interface org.bluez.MediaItem1 [Experimental] Object path freely definable (Target role) [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX/playerX/itemX (Controller role) Methods void Play() Play item Possible Errors: org.bluez.Error.NotSupported org.bluez.Error.Failed void AddtoNowPlaying() Add item to now playing list Possible Errors: org.bluez.Error.NotSupported org.bluez.Error.Failed Properties object Player [readonly] Player object path the item belongs to string Name [readonly] Item displayable name string Type [readonly] Item type Possible values: "video", "audio", "folder" string FolderType [readonly, optional] Folder type. Possible values: "mixed", "titles", "albums", "artists" Available if property Type is "Folder" boolean Playable [readonly, optional] Indicates if the item can be played Available if property Type is "folder" dict Metadata [readonly] Item metadata. Possible values: string Title Item title name Available if property Type is "audio" or "video" string Artist Item artist name Available if property Type is "audio" or "video" string Album Item album name Available if property Type is "audio" or "video" string Genre Item genre name Available if property Type is "audio" or "video" uint32 NumberOfTracks Item album number of tracks in total Available if property Type is "audio" or "video" uint32 Number Item album number Available if property Type is "audio" or "video" uint32 Duration Item duration in milliseconds Available if property Type is "audio" or "video" MediaEndpoint1 hierarchy ======================== Service unique name Interface org.bluez.MediaEndpoint1 Object path freely definable Methods void SetConfiguration(object transport, dict properties) Set configuration for the transport. array{byte} SelectConfiguration(array{byte} capabilities) Select preferable configuration from the supported capabilities. Returns a configuration which can be used to setup a transport. Note: There is no need to cache the selected configuration since on success the configuration is send back as parameter of SetConfiguration. void ClearConfiguration(object transport) Clear transport configuration. void Release() This method gets called when the service daemon unregisters the endpoint. An endpoint can use it to do cleanup tasks. There is no need to unregister the endpoint, because when this method gets called it has already been unregistered. MediaTransport1 hierarchy ========================= Service org.bluez Interface org.bluez.MediaTransport1 Object path [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX/fdX Methods fd Acquire() Acquire transport file descriptor and the MTU for read and write respectively. Possible Errors: org.bluez.Error.NotAuthorized org.bluez.Error.Failed fd TryAcquire() Acquire transport file descriptor only if the transport is in "pending" state at the time the message is received by BlueZ. Otherwise no request will be sent to the remote device and the function will just fail with org.bluez.Error.NotAvailable. Possible Errors: org.bluez.Error.NotAuthorized org.bluez.Error.Failed org.bluez.Error.NotAvailable void Release() Releases file descriptor. Properties object Device [readonly] Device object which the transport is connected to. string UUID [readonly] UUID of the profile which the transport is for. byte Codec [readonly] Assigned number of codec that the transport support. The values should match the profile specification which is indicated by the UUID. array{byte} Configuration [readonly] Configuration blob, it is used as it is so the size and byte order must match. string State [readonly] Indicates the state of the transport. Possible values are: "idle": not streaming "pending": streaming but not acquired "active": streaming and acquired uint16 Delay [readwrite] Optional. Transport delay in 1/10 of millisecond, this property is only writeable when the transport was acquired by the sender. boolean NREC [readwrite] Optional and HFP specific (external to BlueZ). Indicates if echo cancelling and noise reduction functions are active in the transport, this property is only writeable when the transport was acquired by the sender. boolean InbandRingtone [readwrite] Optional and HFP specific (external to BlueZ). Indicates if the transport support sending ringtones, this property is only writeable when the transport was acquired by the sender. string Routing [readonly] Optional and HFP specific (external to BlueZ). Indicates where is the transport being routed. Possible Values: "HCI" or "PCM" uint16 Volume [readwrite] Optional. Indicates volume level of the transport, this property is only writeable when the transport was acquired by the sender. Note: the property will not be present for HSP/HFP transports and MicrophoneGain/SpeakerGain should be used instead. Possible Values: 0-127 byte MicrophoneGain [readwrite] Optional. Indicates volume level of the transport's incoming audio stream for HSP/HFP transports. This property is only writeable when the transport was acquired by the sender. Possible Values: 0-15 byte SpeakerGain [readwrite] Optional. Indicates volume level of the transport's outgoing audio stream for HSP/HFP transports. This property is only writeable when the transport was acquired by the sender. Possible Values: 0-15 bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/mgmt-api.txt000066400000000000000000001745361315563672100254130ustar00rootroot00000000000000Bluetooth Management API ************************* Copyright (C) 2008-2009 Marcel Holtmann Overview ======== This document describes the format of data used for communicating with the kernel using a so-called Bluetooth Management sockets. These sockets are available starting with Linux kernel version 3.4 The following kernel versions introduced new commands, new events or important fixes to the Bluetooth Management API: Linux kernel v3.4 Version 1.0 Linux kernel v3.5 Version 1.1 Linux kernel v3.7 Version 1.2 Linux kernel v3.9 Version 1.3 Linux kernel v3.13 Version 1.4 Linux kernel v3.15 Version 1.5 Linux kernel v3.16 Version 1.6 (not yet released) Version 1.1 introduces Set Device ID command. Version 1.2 introduces Passkey Notify event. Version 1.3 does not introduce any new command or event. Version 1.4 introduces Set Advertising, Set BR/EDR, Set Static Address and Set Scan Parameters commands. Version 1.5 introduces Set Secure Connections, Set Debug Keys, Set Privacy and Load Identity Resolving Keys commands. It also introduces New Identity Resolving Key and New Signature Resolving Key events. Version 1.6 introduces Get Connection Information command. It also updates the Device Found event to combine advertising data and scan response data into a single event. Example ======= The Bluetooth management sockets can be created by setting the hci_channel member of struct sockaddr_hci to HCI_CHANNEL_CONTROL (3) when creating a raw HCI socket. In C the needed code would look something like the following: int mgmt_create(void) { struct sockaddr_hci addr; int fd; fd = socket(PF_BLUETOOTH, SOCK_RAW | SOCK_CLOEXEC | SOCK_NONBLOCK, BTPROTO_HCI); if (fd < 0) return -errno; memset(&addr, 0, sizeof(addr)); addr.hci_family = AF_BLUETOOTH; addr.hci_dev = HCI_DEV_NONE; addr.hci_channel = HCI_CHANNEL_CONTROL; if (bind(fd, (struct sockaddr *) &addr, sizeof(addr)) < 0) { int err = -errno; close(fd); return err; } return fd; } The process creating the mgmt socket is required to have the CAP_NET_ADMIN capability (e.g. root would have this). Packet Structures ================= Commands: 0 4 8 12 16 22 24 28 31 35 39 43 47 +-------------------+-------------------+-------------------+ | Command Code | Controller Index | Parameter Length | +-------------------+-------------------+-------------------+ | | Events: 0 4 8 12 16 22 24 28 31 35 39 43 47 +-------------------+-------------------+-------------------+ | Event Code | Controller Index | Parameter Length | +-------------------+-------------------+-------------------+ | | All fields are in little-endian byte order (least significant byte first). Controller Index can have a special value to indicate that command or event is not related to any controller. Possible values: 0x0000 to 0xFFFE 0xFFFF Error Codes =========== The following values have been defined for use with the Command Status and Command Complete events: 0x00 Success 0x01 Unknown Command 0x02 Not Connected 0x03 Failed 0x04 Connect Failed 0x05 Authentication Failed 0x06 Not Paired 0x07 No Resources 0x08 Timeout 0x09 Already Connected 0x0A Busy 0x0B Rejected 0x0C Not Supported 0x0D Invalid Parameters 0x0E Disconnected 0x0F Not Powered 0x10 Cancelled 0x11 Invalid Index Read Management Version Information Command =========================================== Command Code: 0x0001 Controller Index: Command Parameters: Return Parameters: Version (1 Octets) Revision (2 Octets) This command returns the Management version and revision. Besides, being informational the information can be used to determine whether certain behavior has changed or bugs fixed when interacting with the kernel. This command generates a Command Complete event on success or a Command Status event on failure. Read Management Supported Commands Command ========================================== Command Code: 0x0002 Controller Index: Command Parameters: Return Parameters: Num_Of_Commands (2 Octets) Num_Of_Events (2 Octets) Command1 (2 Octets) Command2 (2 Octets) ... Event1 (2 Octets) Event2 (2 Octets) ... This command returns the list of supported Management commands and events. The commands Read Management Version Information and Read management Supported Commands are not included in this list. Both commands are always supported and mandatory. The events Command Status and Command Complete are not included in this list. Both are implicit and mandatory. This command generates a Command Complete event on success or a Command Status event on failure. Read Controller Index List Command ================================== Command Code: 0x0003 Controller Index: Command Parameters: Return Parameters: Num_Controllers (2 Octets) Controller_Index[i] (2 Octets) This command returns the list of currently known controllers. Controllers added or removed after calling this command can be monitored using the Index Added and Index Removed events. This command generates a Command Complete event on success or a Command Status event on failure. Read Controller Information Command =================================== Command Code: 0x0004 Controller Index: Command Parameters: Return Parameters: Address (6 Octets) Bluetooth_Version (1 Octet) Manufacturer (2 Octets) Supported_Settings (4 Octets) Current_Settings (4 Octets) Class_Of_Device (3 Octets) Name (249 Octets) Short_Name (11 Octets) This command is used to retreive the current state and basic information of a controller. It is typically used right after getting the response to the Read Controller Index List command or an Index Added event. If not short name is set the Short_Name parameter will be empty (begin with a nul byte). Current_Settings & Supported_Settings is a bitmask with currently the following available bits: 0 Powered 1 Connectable 2 Fast Connectable 3 Discoverable 4 Pairable 5 Link Level Security (Sec. mode 3) 6 Secure Simple Pairing 7 Basic Rate/Enhanced Data Rate 8 High Speed 9 Low Energy 10 Advertising 11 Secure Connections 12 Debug Keys 13 Privacy This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Invalid Parameters Invalid Index Set Powered Command =================== Command Code: 0x0005 Controller Index: Command Parameters: Powered (1 Octet) Return Parameters: Current_Settings (4 Octets) This command is used to power on or off a controller. The allowed Powered command parameter values are 0x00 and 0x01. All other values will return Invalid Parameters. If discoverable setting is activated with a timeout, then switching the controller off will expire this timeout and disable discoverable. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Busy Invalid Parameters Invalid Index Set Discoverable Command ======================== Command Code: 0x0006 Controller Index: Command Parameters: Discoverable (1 Octet) Timeout (2 Octets) Return Parameters: Current_Settings (4 Octets) This command is used to set the discoverable property of a controller. The allowed Discoverable command parameter values are 0x00, 0x01 and 0x02. All other values will return Invalid Parameters. Timeout is the time in seconds and is only meaningful when Discoverable is set to 0x01 or 0x02. Providing a timeout with 0x00 return Invalid Parameters. For 0x02, the timeout value is required. The value 0x00 disables discoverable, the value 0x01 enables general discoverable and the value 0x02 enables limited discoverable. This command is only available for BR/EDR capable controllers (e.g. not for single-mode LE ones). It will return Not Supported otherwise. This command can be used when the controller is not powered and all settings will be programmed once powered. However using a timeout when the controller is not powered will return Not Powered error. When switching discoverable on and the connectable setting is off it will return Rejected error. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Busy Rejected Not Supported Invalid Parameters Not Powered Invalid Index Set Connectable Command ======================= Command Code: 0x0007 Controller Index: Command Parameters: Connectable (1 Octet) Return Parameters: Current_Settings (4 Octets) This command is used to set the connectable property of a controller. The allowed Connectable command parameter values are 0x00 and 0x01. All other values will return Invalid Parameters. This command is available for BR/EDR, LE-only and also dual mode controllers. For BR/EDR is changes the page scan setting and for LE controllers it changes the advertising type. For dual mode controllers it affects both settings. For LE capable controllers the connectable setting only takes affect when advertising is enabled. This command can be used when the controller is not powered and all settings will be programmed once powered. When switching connectable off, it will also switch off the discoverable setting. Switching connectable back on will not restore a previous discoverable. It will stay off and needs to be manually switched back on. When switching connectable off, it will expire a discoverable setting with a timeout. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Busy Not Supported Invalid Parameters Invalid Index Set Fast Connectable Command ============================ Command Code: 0x0008 Controller Index: Command Parameters: Enable (1 Octet) Return Parameters: Current_Settings (4 Octets) This command is used to set the controller into a connectable state where the page scan parameters have been set in a way to favor faster connect times with the expense of higher power consumption. The allowed values of the Enable command parameter are 0x00 and 0x01. All other values will return Invalid Parameters. This command is only available for BR/EDR capable controllers (e.g. not for single-mode LE ones). It will return Not Supported otherwise. This command can only be used when the controller is powered on and will return Not Powerd otherwise. If connectable is not set, then this command will fail with Rejected error. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Failed Busy Rejected Not Supported Invalid Parameters Not Powered Invalid Index Set Pairable Command ==================== Command Code: 0x0009 Controller Index: Command Parameters: Pairable (1 Octet) Return Parameters: Current_Settings (4 Octets) This command is used to set the pairable property of an controller. The allowed values for the Pairable command parameter are 0x00 and 0x01. All other values will return Invalid Parameters. This command can be used when the controller is not powered and all settings will be programmed once powered. Turning pairable on will not automatically switch the controller into connectable mode. That needs to be done separately. The setting will be remembered during power down/up toggles. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Invalid Parameters Invalid Index Set Link Security Command ========================= Command Code: 0x000A Controller Index: Command Parameters: Link_Security (1 Octet) Return Parameters: Current_Settings (4 Octets) This command is used to either enable or disable link level security for an controller (also known as Security Mode 3). The allowed values for the Link_Security command parameter are 0x00 and 0x01. All other values will return Invalid Parameters. This command is only available for BR/EDR capable controllers (e.g. not for single-mode LE ones). It will return Not Supported otherwise. This command can be used when the controller is not powered and all settings will be programmed once powered. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Busy Not Supported Invalid Parameters Invalid Index Set Secure Simple Pairing Command ================================= Command Code: 0x000B Controller Index: Command Parameters: Secure_Simple_Pairing (1 Octet) Return Parameters: Current_Settings (4 Octets) This command is used to enable/disable Secure Simple Pairing support for a controller. The allowed values for the Secure_Simple_Pairing command parameter are 0x00 and 0x01. All other values will return Invalid Parameters. This command is only available for BR/EDR capable controllers supporting the core specification version 2.1 or greater (e.g. not for single-mode LE controllers or pre-2.1 ones). This command can be used when the controller is not powered and all settings will be programmed once powered. In case the controller does not support Secure Simple Pairing, the command will fail regardless with Not Supported error. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Busy Not Supported Invalid Parameters Invalid Index Set High Speed Command ====================== Command Code: 0x000C Controller Index: Command Parameters: High_Speed (1 Octet) Return Parameters: Current_Settings (4 Octets) This command is used to enable/disable Bluetooth High Speed support for a controller. The allowed values for the High_Speed command parameter are 0x00 and 0x01. All other values will return Invalid Parameters. This command is only available for BR/EDR capable controllers (e.g. not for single-mode LE ones). This command can be used when the controller is not powered and all settings will be programmed once powered. To enable High Speed support, it is required that Secure Simple Pairing support is enabled first. High Speed support is not possible for connections without Secure Simple Pairing. When switching Secure Simple Pairing off, the support for High Speed will be switched off as well. Switching Secure Simple Pairing back on, will not re-enable High Speed support. That needs to be done manually. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Not Supported Invalid Parameters Invalid Index Set Low Energy Command ====================== Command Code: 0x000D Controller Index: Command Parameters: Low_Energy (1 Octet) Return Parameters: Current_Settings (4 Octets) This command is used to enable/disable Low Energy support for a controller. The allowed values of the Low_Energy command parameter are 0x00 and 0x01. All other values will return Invalid Parameters. This command is only available for LE capable controllers and will yield in a Not Supported error otherwise. This command can be used when the controller is not powered and all settings will be programmed once powered. In case the kernel subsystem does not support Low Energy or the controller does not either, the command will fail regardless. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Busy Not Supported Invalid Parameters Invalid Index Set Device Class ================ Command Code: 0x000E Controller Index: Command Parameters: Major_Class (1 Octet) Minor_Class (1 Octet) Return Parameters: Class_Of_Device (3 Octets) This command is used to set the major and minor device class for BR/EDR capable controllers. This command will also implicitly disable caching of pending CoD and EIR updates. This command is only available for BR/EDR capable controllers (e.g. not for single-mode LE ones). This command can be used when the controller is not powered and all settings will be programmed once powered. In case the controller is powered off, 0x000000 will be returned for the class of device parameter. And after power on the new value will be announced via class of device changed event. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Busy Not Supported Invalid Parameters Invalid Index Set Local Name Command ====================== Command Code: 0x000F Controller Index: Command Parameters: Name (249 Octets) Short_Name (11 Octets) Return Parameters: Name (249 Octets) Short_Name (11 Octets) This command is used to set the local name of a controller. The command parameters also include a short name which will be used in case the full name doesn't fit within EIR/AD data. The name parameters need to always end with a null byte (failure to do so will cause the command to fail). This command can be used when the controller is not powered and all settings will be programmed once powered. The values of name and short name will be remembered when switching the controller off and back on again. So the name and short name only have to be set once when a new controller is found and will stay until removed. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Invalid Parameters Invalid Index Add UUID Command ================ Command Code: 0x0010 Controller Index: Command Parameters: UUID (16 Octets) SVC_Hint (1 Octet) Return Parameters: Class_Of_Device (3 Octets) This command is used to add a UUID to be published in EIR and/or AD data. The accompanied SVC_Hint parameter is used to tell the kernel whether the service class bits of the Class of Device value need modifying due to this UUID. This command can be used when the controller is not powered and all settings will be programmed once powered. In case the controller is powered off, 0x000000 will be returned for the class of device parameter. And after power on the new value will be announced via class of device changed event. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Busy Invalid Parameters Invalid Index Remove UUID Command =================== Command Code: 0x0011 Controller Index: Command Parameters: UUID (16 Octets) Return Parameters: Class_Of_Device (3 Octets) This command is used to remove a UUID previously added using the Add UUID command. When the UUID parameter is an empty UUID (16 x 0x00), then all previously loaded UUIDs will be removed. This command can be used when the controller is not powered and all settings will be programmed once powered. In case the controller is powered off, 0x000000 will be returned for the class of device parameter. And after power on the new value will be announced via class of device changed event. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Busy Invalid Parameters Invalid Index Load Link Keys Command ====================== Command Code: 0x0012 Controller Index: Command Parameters: Debug_Keys (1 Octet) Key_Count (2 Octets) Key1 { Address (6 Octets) Address_Type (1 Octet) Key_Type (1 Octet) Value (16 Octets) PIN_Length (1 Octet) } Key2 { } ... Return Parameters: This command is used to feed the kernel with currently known link keys. The command does not need to be called again upon the receiption of New Link Key events since the kernel updates its list automatically. The Debug_Keys parameter is used to tell the kernel whether to accept the usage of debug keys or not. The allowed values for this parameter are 0x00 and 0x01. All other values will return an Invalid Parameters response. Usage of the Debug_Keys parameter is deprecated and has been replaced with the Set Debug Keys command. When setting the Debug_Keys option via Load Link Keys command it has the same affect as setting it via Set Debug Keys and applies to all keys in the system. Possible values for the Address_Type parameter: 0 BR/EDR 1 Reserved (not in use) 2 Reserved (not in use) Public and random LE addresses are not valid and will be rejected. Currently defined Key_Type values are: 0x00 Combination key 0x01 Local Unit key 0x02 Remote Unit key 0x03 Debug Combination key 0x04 Unauthenticated Combination key from P-192 0x05 Authenticated Combination key from P-192 0x06 Changed Combination key 0x07 Unauthenticated Combination key from P-256 0x08 Authenticated Combination key from P-256 This command can be used when the controller is not powered. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Invalid Parameters Invalid Index Load Long Term Keys Command =========================== Command Code: 0x0013 Controller Index: Command Parameters: Key_Count (2 Octets) Key1 { Address (6 Octets) Address_Type (1 Octet) Key_Type (1 Octet) Master (1 Octet) Encryption_Size (1 Octet) Encryption_Diversifier (2 Octets) Random_Number (8 Octets) Value (16 Octets) } Key2 { } ... Return Parameters: This command is used to feed the kernel with currently known (SMP) Long Term Keys. The command does not need to be called again upon the receiption of New Long Term Key events since the kernel updates its list automatically. Possible values for the Address_Type parameter: 0 Reserved (not in use) 1 LE Public 2 LE Random The provided Address and Address_Type are the identity of a device. So either its public address or static random address. Unresolvable random addresses and resolvable random addresses are not valid and will be rejected. Currently defined Key_Type values are: 0x00 Unauthenticated key 0x01 Authenticated key This command can be used when the controller is not powered. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Invalid Parameters Invalid Index Disconnect Command ================== Command Code: 0x0014 Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Return Parameters: Address (6 Octets) Address_Type (1 Octet) This command is used to force the disconnection of a currently connected device. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random This command can only be used when the controller is powered. This command generates a Command Complete event on success or failure. Possible errors: Not Connected Busy Invalid Parameters Not Powered Invalid Index Get Connections Command ======================= Command Code: 0x0015 Controller Index: Command Parameters: Return Parameters: Connection_Count (2 Octets) Address1 { Address (6 Octets) Address_Type (1 Octet) } Address2 { } ... This command is used to retreive a list of currently connected devices. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random For devices using resolvable random addresses with a known identity resolving key, the Address and Address_Type will contain the identity information. This command can only be used when the controller is powered. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Invalid Parameters Not Powered Invalid Index PIN Code Reply Command ======================= Command Code: 0x0016 Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) PIN_Length (1 Octet) PIN_Code (16 Octets) Return Parameters: Address (6 Octets) Address_Type (1 Octet) This command is used to respond to a PIN Code request event. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random This command can only be used when the controller is powered. This command generates a Command Complete event on success or failure. Possible errors: Not Connected Invalid Parameters Not Powered Invalid Index PIN Code Negative Reply Command =============================== Command Code: 0x0017 Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Return Parameters: Address (6 Octets) Address_Type (1 Octet) This command is used to return a negative response to a PIN Code Request event. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random This command can only be used when the controller is powered. This command generates a Command Complete event on success or failure. Possible errors: Not Connected Invalid Parameters Not Powered Invalid Index Set IO Capability Command ========================= Command Code: 0x0018 Controller Index: Command Parameters: IO_Capability (1 Octet) Return Parameters: This command is used to set the IO Capability used for pairing. The command accepts both SSP and SMP values. Possible values for the IO_Capability parameter: 0 DisplayOnly 1 DisplayYesNo 2 KeyboardOnly 3 NoInputNoOutput 4 KeyboardDisplay Passing a value 4 (KeyboardDisplay) will cause the kernel to convert it to 1 (DisplayYesNo) in the case of a BR/EDR connection (as KeyboardDisplay is specific to SMP). This command can be used when the controller is not powered. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Invalid Parameters Invalid Index Pair Device Command =================== Command Code: 0x0019 Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) IO_Capability (1 Octet) Return Parameters: Address (6 Octets) Address_Type (1 Octet) This command is used to trigger pairing with a remote device. The IO_Capability command parameter is used to temporarily (for this pairing event only) override the global IO Capaility (set using the Set IO Capability command). Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random Possible values for the IO_Capability parameter: 0 DisplayOnly 1 DisplayYesNo 2 KeyboardOnly 3 NoInputNoOutput 4 KeyboardDisplay Passing a value 4 (KeyboardDisplay) will cause the kernel to convert it to 1 (DisplayYesNo) in the case of a BR/EDR connection (as KeyboardDisplay is specific to SMP). The Address and Address_Type of the return parameters will return the identity address if know. In case of resolvable random address given as command parameters and the remote provides an identity resolving key, the return parameters will provide the resolved address. To allow tracking of which resolvable random address changed into which identity address, the New Identity Resolving Key event will be send before receiving Command Complete event for this command. This command can only be used when the controller is powered. This command generates a Command Complete event on success or failure. Possible errors: Connect Failed Busy Invalid Parameters Not Powered Invalid Index Cancel Pair Device ================== Command Code: 0x001A Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Return Parameters: Address (6 Octets) Address_Type (1 Octet) The Address and Address_Type parameters should match what was given to a preceding Pair Device command. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random This command can only be used when the controller is powered. This command generates a Command Complete event on success or failure. Possible errors: Invalid Parameters Not Powered Invalid Index Unpair Device Command ===================== Command Code: 0x001B Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Disconnect (1 Octet) Return Parameters: Address (6 Octets) Address_Type (1 Octet) Removes all keys associated with the remote device. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random The Disconnect parameter tells the kernel whether to forcefully disconnect any existing connections to the device. It should in practice always be 1 except for some special GAP qualification test-cases where a key removal without disconnecting is needed. When unpairing a device its link key, long term key and if provided identity resolving key will be purged. For devices using resolvable random addresses where the identity resolving key was available, after this command they will now no longer be resolved. The device will essentially become private again. This command can only be used when the controller is powered. This command generates a Command Complete event on success or failure. Possible errors: Not Paired Invalid Parameters Not Powered Invalid Index User Confirmation Reply Command =============================== Command Code: 0x001C Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Return Parameters: Address (6 Octets) Address_Type (1 Octet) This command is used to respond to a User Confirmation Request event. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random This command can only be used when the controller is powered. This command generates a Command Complete event on success or failure. Possible errors: Not Connected Invalid Parameters Not Powered Invalid Index User Confirmation Negative Reply Command ======================================== Command Code: 0x001D Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Return Parameters: Address (6 Octets) Address_Type (1 Octet) This command is used to return a negative response to a User Confirmation Request event. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random This command can only be used when the controller is powered. This command generates a Command Complete event on success or failure. Possible errors: Not Connected Invalid Parameters Not Powered Invalid Index User Passkey Reply Command ========================== Command Code: 0x001E Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Passkey (4 Octets) Return Parameters: Address (6 Octets) Address_Type (1 Octet) This command is used to respond to a User Confirmation Passkey Request event. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random This command can only be used when the controller is powered. This command generates a Command Complete event on success or failure. Possible errors: Not Connected Invalid Parameters Not Powered Invalid Index User Passkey Negative Reply Command =================================== Command Code: 0x001F Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Return Parameters: Address (6 Octets) Address_Type (1 Octet) This command is used to return a negative response to a User Passkey Request event. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random This command can only be used when the controller is powered. This command generates a Command Complete event on success or failure. Possible errors: Not Connected Invalid Parameters Not Powered Invalid Index Read Local Out Of Band Data Command =================================== Command Code: 0x0020 Controller Index: Command Parameters: Return Parameters: Hash_192 (16 Octets) Randomizer_192 (16 Octets) Hash_256 (16 Octets, Optional) Randomizer_256 (16 Octets, Optional) This command is used to read the local Out of Band data. This command can only be used when the controller is powered. If Secure Connections support is enabled, then this command will return P-192 versions of hash and randomizer as well as P-256 versions of both. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Not Supported Busy Invalid Parameters Not Powered Invalid Index Add Remote Out Of Band Data Command =================================== Command Code: 0x0021 Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Hash_192 (16 Octets) Randomizer_192 (16 Octets) Hash_256 (16 Octets, Optional) Randomizer_256 (16 Octets, Optional) Return Parameters: Address (6 Octets) Address_Type (1 Octet) This command is used to provide Out of Band data for a remote device. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random Provided Out Of Band data is persistent over power down/up toggles. This command also accept optional P-256 versions of hash and randomizer. If they are not provided, then they are set to zero value. The P-256 versions of both can also be provided when the support for Secure Connections is not enabled. However in that case they will never be used. To only provide the P-256 versions of hash and randomizer, it is valid to leave both P-192 fields as zero values. If Secure Connections is disabled, then of course this is the same as not providing any data at all. This command generates a Command Complete event on success or failure. Possible errors: Failed Invalid Parameters Not Powered Invalid Index Remove Remote Out Of Band Data Command ====================================== Command Code: 0x0022 Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Return Parameters: Address (6 Octets) Address_Type (1 Octet) This command is used to remove data added using the Add Remote Out Of Band Data command. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random This command generates a Command Complete event on success or failure. Possible errors: Invalid Parameters Not Powered Invalid Index Start Discovery Command ======================= Command Code: 0x0023 Controller Index: Command Parameters: Address_Type (1 Octet) Return Parameters: Address_Type (1 Octet) This command is used to start the process of discovering remote devices. A Device Found event will be sent for each discovered device. Possible values for the Address_Type parameter are a bit-wise or of the following bits: 0 BR/EDR 1 LE Public 2 LE Random By combining these e.g. the following values are possible: 1 BR/EDR 6 LE (public & random) 7 BR/EDR/LE (interleaved discovery) This command can only be used when the controller is powered. This command generates a Command Complete event on success or failure. Possible errors: Busy Not Supported Invalid Parameters Not Powered Invalid Index Stop Discovery Command ====================== Command Code: 0x0024 Controller Index: Command Parameters: Address_Type (1 Octet) Return Parameters: Address_Type (1 Octet) This command is used to stop the discovery process started using the Start Discovery command. This command can only be used when the controller is powered. This command generates a Command Complete event on success or failure. Possible errors: Rejected Invalid Parameters Invalid Index Confirm Name Command ==================== Command Code: 0x0025 Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Name_Known (1 Octet) Return Parameters: Address (6 Octets) Address_Type (1 Octet) This command is only valid during device discovery and is expected for each Device Found event with the Confirm Name flag set. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random The Name_Known parameter should be set to 0x01 if user space knows the name for the device and 0x00 if it doesn't. If set to 0x00 the kernel will perform a name resolving procedure for the device in question. This command can only be used when the controller is powered. This command generates a Command Complete event on success or failure. Possible errors: Failed Invalid Parameters Invalid Index Block Device Command ==================== Command Code: 0x0026 Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Return Parameters: Address (6 Octets) Address_Type (1 Octet) This command is used to add a device to the list of devices which should be blocked from being connect to the local controller. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random This command can be used when the controller is not powered. This command generates a Command Complete event on success or failure. Possible errors: Failed Invalid Parameters Invalid Index Unblock Device Command ====================== Command Code: 0x0027 Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Return Parameters: Address (6 Octets) Address_Type (1 Octet) This command is used to remove a device from the list of blocked devices (where it was added to using the Block Device command). Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random This command can be used when the controller is not powered. This command generates a Command Complete event on success or failure. Possible errors: Invalid Parameters Invalid Index Set Device ID Command ===================== Command Code: 0x0028 Controller Index: Command Parameters: Source (2 Octets) Vendor (2 Octets) Product (2 Octets) Version (2 Octets) Return Parameters: This command can be used when the controller is not powered and all settings will be programmed once powered. The Source parameter selects the organization that assigned the Vendor parameter: 0x0000 Disable Device ID 0x0001 Bluetooth SIG 0x0002 USB Implementer’s Forum The information are put into the EIR data. If the controller does not support EIR or if SSP is disabled, this command will still succeed. The information are stored for later use and will survive toggling SSP on and off. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Invalid Parameters Invalid Index Set Advertising Command ======================= Command Code: 0x0029 Controller Index: Command Parameters: Advertising (1 Octet) Return Parameters: Current_Settings (4 Octets) This command is used to enable LE advertising on a controller that supports it. The allowed values for the Advertising command parameter are 0x00 and 0x01. All other values will return Invalid Parameters. A pre-requisite is that LE is already enabled, otherwise this command will return a "rejected" response. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Busy Rejected Not Supported Invalid Parameters Invalid Index Set BR/EDR Command ================== Command Code: 0x002A Controller Index: Command Parameters: BR/EDR (1 Octet) Return Parameters: Current_Settings (4 Octets) This command is used to enable or disable BR/EDR support on a dual-mode controller. The allowed values for the Advertising command parameter are 0x00 and 0x01. All other values will return Invalid Parameters. A pre-requisite is that LE is already enabled, otherwise this command will return a "rejected" response. Enabling BR/EDR can be done both when powered on and powered off, however disabling it can only be done when powered off (otherwise the command will again return "rejected"). Disabling BR/EDR will automatically disable all other BR/EDR related settings. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Busy Rejected Not Supported Invalid Parameters Invalid Index Set Static Address Command ========================== Command Code: 0x002B Controller Index: Command Parameters: Address (6 Octets) Return Parameters: This command allows for setting the static random address. It is only supported on controllers with LE support. The static random address is suppose to be valid for the lifetime of the controller or at least until the next power cycle. To ensure such behavior, setting of the address is limited to when the controller is powered off. The special BDADDR_ANY address (00:00:00:00:00:00) can be used to disable the static address. When a controller has a public address (which is required for all dual-mode controllers), this address is not used. Only when the controller information reports BDADDR_ANY (00:00:00:00:00:00), it is required to configure a static address first. If privacy mode is enabled and the controller is single mode LE only without a public address, the static random address is used as identity address. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Rejected Not Supported Invalid Parameters Invalid Index Set Scan Parameters Command =========================== Command Code: 0x002C Controller Index: Command Parameters: Interval (2 Octets) Window (2 Octets) Return Parameters: This command allows for setting the Low Energy scan parameters used for connection establishment and passive scanning. It is only supported on controllers with LE support. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Rejected Not Supported Invalid Parameters Invalid Index Set Secure Connections Command ============================== Command Code: 0x002D Controller Index: Command Parameters: Secure_Connections (1 Octet) Return Parameters: Current_Settings (4 Octets) This command is used to enable/disable Secure Connections support for a controller. The allowed values for the Secure_Connections command parameter are 0x00, 0x01 and 0x02. All other values will return Invalid Parameters. The value 0x00 disables Secure Connections, the value 0x01 enables Secure Connections and the value 0x02 enables Secure Connections Only mode. This command is only available for BR/EDR capable controllers supporting the core specification version 4.1 or greater (e.g. not for single-mode LE controllers or pre-4.1 ones). This command can be used when the controller is not powered and all settings will be programmed once powered. In case the controller does not support Secure Connections the command will fail regardless with Not Supported error. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Busy Not Supported Invalid Parameters Invalid Index Set Debug Keys Command ====================== Command Code: 0x002E Controller Index: Command Parameters: Debug_Keys (1 Octet) Return Parameters: Current_Settings (4 Octets) This command is used to tell the kernel whether to accept the usage of debug keys or not. The allowed values for this parameter are 0x00 and 0x01. All other values will return an Invalid Parameters response. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Busy Not Supported Invalid Parameters Invalid Index Set Privacy Command =================== Command Code: 0x002F Controller Index: Command Parameters: Privacy (1 Octet) Identity_Resolving_Key (16 Octets) Return Parameters: Current_Settings (4 Octets) This command is used to enable Low Energy Privacy feature using resolvable private addresses. The value 0x00 disables privacy mode, the value 0x01 enables privacy mode. When the controller has a public address (mandatory for dual-mode controllers) it is used as identity address. In case the controller is single mode LE only without a public address, it is required to configure a static random andress first. The privacy mode can only be enabled when an identity address is available. The Identity_Resolving_Key is the local key assigned for the local resolvable private address. Possible errors: Busy Not Supported Invalid Parameters Invalid Index Load Identity Resolving Keys Command ==================================== Command Code: 0x0030 Controller Index: Command Parameters: Key_Count (2 Octets) Key1 { Address (6 Octets) Address_Type (1 Octet) Value (16 Octets) } Key2 { } ... Return Parameters: This command is used to feed the kernel with currently known identity resolving keys. The command does not need to be called again upon the receiption of New Identity Resolving Key events since the kernel updates its list automatically. Possible values for the Address_Type parameter: 0 Reserved (not in use) 1 LE Public 2 LE Random The provided Address and Address_Type are the identity of a device. So either its public address or static random address. Unresolvable random addresses and resolvable random addresses are not valid and will be rejected. This command can be used when the controller is not powered. This command generates a Command Complete event on success or a Command Status event on failure. Possible errors: Invalid Parameters Invalid Index Get Connection Information Command ================================== Command Code: 0x0031 Controller Index: Command Parameters: Address (6 Octets) Address_Type (1 Octet) Return Parameters: Address (6 Octets) Address_Type (1 Octet) RSSI (1 Octet) TX_Power (1 Octet) Max_TX_Power (1 Octet) This command is used to get connection information. TX_Power and Max_TX_Power can be set to 127 if values are invalid or unknown. This command generates a Command Complete event on success and on failure. In case of failure only Address and Address_Type fields are valid and values of remaining parameters are considered invalid and shall be ignored. Possible errors: Not Connected Not Powered Invalid Parameters Invalid Index Command Complete Event ====================== Event Code: 0x0001 Controller Index: or Event Parameters: Command_Opcode (2 Octets) Status (1 Octet) Return_Parameters This event is an indication that a command has completed. The fixed set of parameters includes the opcode to identify the command that completed as well as a status value to indicate success or failure. The rest of the parameters are command specific and documented in the section for each command separately. Command Status Event ==================== Event Code: 0x0002 Controller Index: or Event Parameters: Command_Opcode (2 Octets) Status (1 Octet) The command status event is used to indicate an early status for a pending command. In the case that the status indicates failure (anything else except success status) this also means that the command has finished executing. Controller Error Event ====================== Event Code: 0x0003 Controller Index: Event Parameters: Error_Code (1 Octet) This event maps straight to the HCI Hardware Error event and is used to indicate something wrong with the controller hardware. Index Added Event ================= Event Code: 0x0004 Controller Index: Event Parameters: This event indicates that a new controller has been added to the system. It is usually followed by a Read Controller Information command. Index Removed Event =================== Event Code: 0x0005 Controller Index: Event Parameters: This event indicates that a controller has been removed from the system. New Settings Event ================== Event Code: 0x0006 Controller Index: Event Parameters: Current_Settings (4 Octets) This event indicates that one or more of the settings for a controller has changed. Class Of Device Changed Event ============================= Event Code: 0x0007 Controller Index: Event Parameters: Class_Of_Device (3 Octets) This event indicates that the Class of Device value for the controller has changed. When the controller is powered off the Class of Device value will always be reported as zero. Local Name Changed Event ======================== Event Code: 0x0008 Controller Index: Event Parameters: Name (249 Octets) Short_Name (11 Octets) This event indicates that the local name of the controller has changed. New Link Key Event ================== Event Code: 0x0009 Controller Index: Event Parameters: Store_Hint (1 Octet) Key { Address (6 Octets) Address_Type (1 Octet) Key_Type (1 Octet) Value (16 Octets) PIN_Length (1 Octet) } This event indicates that a new link key has bee generated for a remote device. The Store_Hint parameter indicates whether the host is expected to store the key persistently or not (e.g. this would not be set if the authentication requirement was "No Bonding"). Possible values for the Address_Type parameter: 0 BR/EDR 1 Reserved (not in use) 2 Reserved (not in use) Public and random LE addresses are not valid and will be rejected. Currently defined Key_Type values are: 0x00 Combination key 0x01 Local Unit key 0x02 Remote Unit key 0x03 Debug Combination key 0x04 Unauthenticated Combination key from P-192 0x05 Authenticated Combination key from P-192 0x06 Changed Combination key 0x07 Unauthenticated Combination key from P-256 0x08 Authenticated Combination key from P-256 Receiving this event indicates that a pairing procecure has been completed. New Long Term Key Event ======================= Event Code: 0x000A Controller Index: Event Parameters: Store_Hint (1 Octet) Key { Address (6 Octets) Address_Type (1 Octet) Key_Type (1 Octet) Master (1 Octet) Encryption Size (1 Octet) Enc. Diversifier (2 Octets) Random Number (8 Octets) Value (16 Octets) } This event indicates that a new long term key has been generated for a remote device. The Store_Hint parameter indicates whether the host is expected to store the key persistently or not (e.g. this would not be set if the authentication requirement was "No Bonding"). Possible values for the Address_Type parameter: 0 Reserved (not in use) 1 LE Public 2 LE Random The provided Address and Address_Type are the identity of a device. So either its public address or static random address. For unresolvable random addresses and resolvable random addresses without identity information and identity resolving key, the Store_Hint will be set to not store the long term key. Currently defined Key_Type values are: 0x00 Unauthenticated key 0x01 Authenticated key Receiving this event indicates that a pairing procecure has been completed. Device Connected Event ====================== Event Code: 0x000B Controller Index: Event Parameters: Address (6 Octets) Address_Type (1 Octet) Flags (4 Octets) EIR_Data_Length (2 Octets) EIR_Data (0-65535 Octets) This event indicates that a successful baseband connection has been created to the remote device. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random For devices using resolvable random addresses with a known identity resolving key, the Address and Address_Type will contain the identity information. It is possible that devices get connected via its resolvable random address and after New Identity Resolving Key event start using its identity. The following bits are defined for the Flags parameter: 0 Reserved (not in use) 1 Legacy Pairing Device Disconnected Event ========================= Event Code: 0x000C Controller Index: Event Parameters: Address (6 Octets) Address_Type (1 Octet) Reason (1 Octet) This event indicates that the baseband connection was lost to a remote device. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random For devices using resolvable random addresses with a known identity resolving key, the Address and Address_Type will contain the identity information. Possible values for the Reason parameter: 0 Unspecified 1 Connection timeout 2 Connection terminated by local host 3 Connection terminated by remote host Note that the local/remote distinction just determines which side terminated the low-level connection, regardless of the disconnection of the higher-level profiles. This can sometimes be misleading and thus must be used with care. For example, some hardware combinations would report a locally initiated disconnection even if the user turned Bluetooth off in the remote side. Connect Failed Event ==================== Event Code: 0x000D Controller Index: Event Parameters: Address (6 Octets) Address_Type (1 Octet) Status (1 Octet) This event indicates that a connection attempt failed to a remote device. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random For devices using resolvable random addresses with a known identity resolving key, the Address and Address_Type will contain the identity information. PIN Code Request Event ====================== Event Code: 0x000E Controller Index: Event Parameters: Address (6 Octets) Address_Type (1 Octet) Secure (1 Octet) This event is used to request a PIN Code reply from user space. The reply should either be returned using the PIN Code Reply or the PIN Code Negative Reply command. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random Secure: 0x01 secure PIN code required 0x00 secure PIN code not required User Confirmation Request Event =============================== Event Code: 0x000F Controller Index: Event Parameters: Address (6 Octets) Address_Type (1 Octet) Confirm_Hint (1 Octet) Value (4 Octets) This event is used to request a user confirmation request from user space. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random If the Confirm_Hint parameter value is 0x01 this means that a simple "Yes/No" confirmation should be presented to the user instead of a full numerical confirmation (in which case the parameter value will be 0x00). User space should respond to this command either using the User Confirmation Reply or the User Confirmation Negative Reply command. User Passkey Request Event ========================== Event Code: 0x0010 Controller Index: Event Parameters: Address (6 Octets) Address_Type (1 Octet) This event is used to request a passkey from user space. The response to this event should either be the User Passkey Reply command or the User Passkey Negative Reply command. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random Authentication Failed Event =========================== Event Code: 0x0011 Controller Index: Event Parameters: Address (6 Octets) Address_Type (1 Octet) Status (1 Octet) This event indicates that there was an authentication failure with a remote device. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random Device Found Event ================== Event Code: 0x0012 Controller Index: Event Parameters: Address (6 Octets) Address_Type (1 Octet) RSSI (1 Octet) Flags (4 Octets) EIR_Data_Length (2 Octets) EIR_Data (0-65535 Octets) This event indicates that a device was found during device discovery. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random The following bits are defined for the Flags parameter: 0 Confirm name 1 Legacy Pairing The Confirm name flag indicates that the kernel wants to know whether user space knows the name for this device or not. If this flag is set user space should respond to it using the Confirm Name command. The Legacy Pairing flag indicates that Legacy Pairing is likely to occur when pairing with this device. An application could use this information to optimize the pairing process by locally pre-generating a PIN code and thereby eliminate the risk of local input timeout when pairing. Note that there is a risk of false-positives for this flag so user space should be able to handle getting something else as a PIN Request when pairing. Discovering Event ================= Event Code: 0x0013 Controller Index: Event Parameters: Address_Type (1 Octet) Discovering (1 Octet) This event indicates that the controller has started discovering devices. This discovering state can come and go multiple times between a StartDiscover and a StopDiscovery command. The valid values for the Discovering parameter are 0x01 (enabled) and 0x00 (disabled). Device Blocked Event ==================== Event Code: 0x0014 Controller Index: Event Parameters: Address (6 Octets) Address_Type (1 Octet) This event indicates that a device has been blocked using the Block Device command. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random The event will only be sent to Management sockets other than the one through which the command was sent. Device Unblocked Event ====================== Event Code: 0x0015 Controller Index: Event Parameters: Address (6 Octets) Address_Type (1 Octet) This event indicates that a device has been unblocked using the Unblock Device command. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random The event will only be sent to Management sockets other than the one through which the command was sent. Device Unpaired Event ===================== Event Code: 0x0016 Controller Index: Event Parameters: Address (6 Octets) Address_Type (1 Octet) This event indicates that a device has been unpaired (i.e. all its keys have been removed from the kernel) using the Unpair Device command. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random For devices using resolvable random addresses with a known identity resolving key, the event paramters will contain the identity. After receiving this event, the device will become essentially private again. The event will only be sent to Management sockets other than the one through which the Unpair Device command was sent. Passkey Notify Event ==================== Event Code: 0x0017 Controller Index: Event Parameters: Address (6 Octets) Address_Type (1 Octet) Passkey (4 Octets) Entered (1 Octet) This event is used to request passkey notification to the user. Unlike the other authentication events it does not need responding to using any Management command. Possible values for the Address_Type parameter: 0 BR/EDR 1 LE Public 2 LE Random The Passkey parameter indicates the passkey to be shown to the user whereas the Entered parameter indicates how many characters the user has entered on the remote side. New Identity Resolving Key Event ================================ Event Code: 0x0018 Controller Index: Event Parameters: Store_Hint (1 Octet) Random_Address (6 Octets) Key { Address (6 Octets) Address_Type (1 Octet) Value (16 Octets) } This event indicates that a new identity resolving key has been generated for a remote device. The Store_Hint parameter indicates whether the host is expected to store the key persistently or not. The Random_Address provides the resolvable random address that was resolved into an identity. A value of 00:00:00:00:00:00 indicates that the identity resolving key was provided for a public address or static random address. Once this event has been send for a resolvable random address, all further events mapping this device will send out using the identity address information. This event also indicates that now the identity address should be used for commands instead of the resolvable random address. Possible values for the Address_Type parameter: 0 Reserved (not in use) 1 LE Public 2 LE Random The provided Address and Address_Type are the identity of a device. So either its public address or static random address. New Signature Resolving Key Event ================================= Event Code: 0x0019 Controller Index: Event Parameters: Store_Hint (1 Octet) Key { Address (6 Octets) Address_Type (1 Octet) Master (1 Octet) Value (16 Octets) } This event indicates that a new signature resolving key has been generated for either the master or slave device. The Store_Hint parameter indicates whether the host is expected to store the key persistently or not. When the Master parameter is set to 0x01, then the signature resolving key from the remote peer device is provided. It is the key that is used for signature verification. When the Master parameter is set to 0x00, then it is the local signature resolving key that is used to sign data. The remote peer device will be using it for signature verification. The local signature resolving key will be generated with each pairing request. Only after receiving this event with Master parameter set to 0x00 it is possible to use ATT Signed Write procedures. Possible values for the Address_Type parameter: 0 Reserved (not in use) 1 LE Public 2 LE Random The provided Address and Address_Type are the identity of a device. So either its public address or static random address. bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/network-api.txt000066400000000000000000000036621315563672100261270ustar00rootroot00000000000000BlueZ D-Bus Network API description *********************************** Network hierarchy ================= Service org.bluez Interface org.bluez.Network1 Object path [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX Methods string Connect(string uuid) Connect to the network device and return the network interface name. Examples of the interface name are bnep0, bnep1 etc. uuid can be either one of "gn", "panu" or "nap" (case insensitive) or a traditional string representation of UUID or a hexadecimal number. The connection will be closed and network device released either upon calling Disconnect() or when the client disappears from the message bus. Possible errors: org.bluez.Error.AlreadyConnected org.bluez.Error.ConnectionAttemptFailed void Disconnect() Disconnect from the network device. To abort a connection attempt in case of errors or timeouts in the client it is fine to call this method. Possible errors: org.bluez.Error.Failed Properties boolean Connected [readonly] Indicates if the device is connected. string Interface [readonly] Indicates the network interface name when available. string UUID [readonly] Indicates the connection role when available. Network server hierarchy ======================== Service org.bluez Interface org.bluez.NetworkServer1 Object path /org/bluez/{hci0,hci1,...} Methods void Register(string uuid, string bridge) Register server for the provided UUID. Every new connection to this server will be added the bridge interface. Valid UUIDs are "gn", "panu" or "nap". Initially no network server SDP is provided. Only after this method a SDP record will be available and the BNEP server will be ready for incoming connections. void Unregister(string uuid) Unregister the server for provided UUID. All servers will be automatically unregistered when the calling application terminates. bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/obex-agent-api.txt000066400000000000000000000032651315563672100264660ustar00rootroot00000000000000OBEX D-Bus Agent API description ******************************** Agent Manager hierarchy ======================= Service org.bluez.obex Interface org.bluez.obex.AgentManager1 Object path /org/bluez/obex Methods void RegisterAgent(object agent) Register an agent to request authorization of the user to accept/reject objects. Object push service needs to authorize each received object. Possible errors: org.bluez.obex.Error.AlreadyExists void UnregisterAgent(object agent) This unregisters the agent that has been previously registered. The object path parameter must match the same value that has been used on registration. Possible errors: org.bluez.obex.Error.DoesNotExist Agent hierarchy =============== Service unique name Interface org.bluez.obex.Agent1 Object path freely definable Methods void Release() This method gets called when the service daemon unregisters the agent. An agent can use it to do cleanup tasks. There is no need to unregister the agent, because when this method gets called it has already been unregistered. string AuthorizePush(object transfer) This method gets called when the service daemon needs to accept/reject a Bluetooth object push request. Returns the full path (including the filename) where the object shall be stored. The tranfer object will contain a Filename property that contains the default location and name that can be returned. Possible errors: org.bluez.obex.Error.Rejected org.bluez.obex.Error.Canceled void Cancel() This method gets called to indicate that the agent request failed before a reply was returned. It cancels the previous request. bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/obex-api.txt000066400000000000000000000477711315563672100254040ustar00rootroot00000000000000OBEX D-Bus API description ************************** Client hierarchy ================ Service org.bluez.obex Interface org.bluez.obex.Client1 Object path /org/bluez/obex Methods object CreateSession(string destination, dict args) Create a new OBEX session for the given remote address. The last parameter is a dictionary to hold optional or type-specific parameters. Typical parameters that can be set in this dictionary include the following: string "Target" : type of session to be created string "Source" : local address to be used byte "Channel" The currently supported targets are the following: "ftp" "map" "opp" "pbap" "sync" Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed void RemoveSession(object session) Unregister session and abort pending transfers. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.NotAuthorized Session hierarchy ================= Service org.bluez.obex Interface org.bluez.obex.Session1 Object path /org/bluez/obex/server/session{0, 1, 2, ...} or /org/bluez/obex/client/session{0, 1, 2, ...} Methods string GetCapabilities() Get remote device capabilities. Possible errors: org.bluez.obex.Error.NotSupported org.bluez.obex.Error.Failed Properties string Source [readonly] Bluetooth adapter address string Destination [readonly] Bluetooth device address byte Channel [readonly] Bluetooth channel string Target [readonly] Target UUID string Root [readonly] Root path Transfer hierarchy ================== Service org.bluez.obex Interface org.bluez.obex.Transfer1 Object path [Session object path]/transfer{0, 1, 2, ...} Methods void Cancel() Stops the current transference. Possible errors: org.bluez.obex.Error.NotAuthorized org.bluez.obex.Error.InProgress org.bluez.obex.Error.Failed void Suspend() Suspend transference. Possible errors: org.bluez.obex.Error.NotAuthorized org.bluez.obex.Error.NotInProgress Note that it is not possible to suspend transfers which are queued which is why NotInProgress is listed as possible error. void Resume() Resume transference. Possible errors: org.bluez.obex.Error.NotAuthorized org.bluez.obex.Error.NotInProgress Note that it is not possible to resume transfers which are queued which is why NotInProgress is listed as possible error. Properties string Status [readonly] Inform the current status of the transfer. Possible values: "queued", "active", "suspended", "complete" or "error" object Session [readonly] The object path of the session the transfer belongs to. string Name [readonly] Name of the transferred object. Either Name or Type or both will be present. string Type [readonly] Type of the transferred object. Either Name or Type or both will be present. uint64 Time [readonly, optional] Time of the transferred object if this is provided by the remote party. uint64 Size [readonly, optional] Size of the transferred object. If the size is unknown, then this property will not be present. uint64 Transferred [readonly, optional] Number of bytes transferred. For queued transfers, this value will not be present. string Filename [readonly, optional] Complete name of the file being received or sent. For incoming object push transaction, this will be the proposed default location and name. It can be overwritten by the AuthorizePush agent callback and will be then updated accordingly. Object Push hierarchy ===================== Service org.bluez.obex Interface org.bluez.obex.ObjectPush1 Object path [Session object path] Methods object, dict SendFile(string sourcefile) Send one local file to the remote device. The returned path represents the newly created transfer, which should be used to find out if the content has been successfully transferred or if the operation fails. The properties of this transfer are also returned along with the object path, to avoid a call to GetProperties. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed object, dict PullBusinessCard(string targetfile) Request the business card from a remote device and store it in the local file. If an empty target file is given, a name will be automatically calculated for the temporary file. The returned path represents the newly created transfer, which should be used to find out if the content has been successfully transferred or if the operation fails. The properties of this transfer are also returned along with the object path, to avoid a call to GetProperties. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed object, dict ExchangeBusinessCards(string clientfile, string targetfile) Push the client's business card to the remote device and then retrieve the remote business card and store it in a local file. If an empty target file is given, a name will be automatically calculated for the temporary file. The returned path represents the newly created transfer, which should be used to find out if the content has been successfully transferred or if the operation fails. The properties of this transfer are also returned along with the object path, to avoid a call to GetProperties. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed File Transfer hierarchy ======================= Service org.bluez.obex Interface org.bluez.obex.FileTransfer Object path [Session object path] Methods void ChangeFolder(string folder) Change the current folder of the remote device. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed void CreateFolder(string folder) Create a new folder in the remote device. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed array{dict} ListFolder() Returns a dictionary containing information about the current folder content. The following keys are defined: string Name : Object name in UTF-8 format string Type : Either "folder" or "file" uint64 Size : Object size or number of items in folder string Permission : Group, owner and other permission uint64 Modified : Last change uint64 Accessed : Last access uint64 Created : Creation date Possible errors: org.bluez.obex.Error.Failed object, dict GetFile(string targetfile, string sourcefile) Copy the source file (from remote device) to the target file (on local filesystem). If an empty target file is given, a name will be automatically calculated for the temporary file. The returned path represents the newly created transfer, which should be used to find out if the content has been successfully transferred or if the operation fails. The properties of this transfer are also returned along with the object path, to avoid a call to GetProperties. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed object, dict PutFile(string sourcefile, string targetfile) Copy the source file (from local filesystem) to the target file (on remote device). The returned path represents the newly created transfer, which should be used to find out if the content has been successfully transferred or if the operation fails. The properties of this transfer are also returned along with the object path, to avoid a call to GetProperties. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed void CopyFile(string sourcefile, string targetfile) Copy a file within the remote device from source file to target file. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed void MoveFile(string sourcefile, string targetfile) Move a file within the remote device from source file to the target file. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed void Delete(string file) Deletes the specified file/folder. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed Phonebook Access hierarchy ========================== Service org.bluez.obex Interface org.bluez.obex.PhonebookAccess1 Object path [Session object path] Methods void Select(string location, string phonebook) Select the phonebook object for other operations. Should be call before all the other operations. location : Where the phonebook is stored, possible inputs : "int" ( "internal" which is default ) "sim" ( "sim1" ) "sim2" ... phonebook : Possible inputs : "pb" : phonebook for the saved contacts "ich": incoming call history "och": outgoing call history "mch": missing call history "cch": combination of ich och mch Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed object, dict PullAll(string targetfile, dict filters) Return the entire phonebook object from the PSE server in plain string with vcard format, and store it in a local file. If an empty target file is given, a name will be automatically calculated for the temporary file. The returned path represents the newly created transfer, which should be used to find out if the content has been successfully transferred or if the operation fails. The properties of this transfer are also returned along with the object path, to avoid a call to GetProperties. Possible filters: Format, Order, Offset, MaxCount and Fields Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Forbidden array{string vcard, string name} List(dict filters) Return an array of vcard-listing data where every entry consists of a pair of strings containing the vcard handle and the contact name. For example: "1.vcf" : "John" Possible filters: Order, Offset and MaxCount Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Forbidden object, dict Pull(string vcard, string targetfile, dict filters) Given a vcard handle, retrieve the vcard in the current phonebook object and store it in a local file. If an empty target file is given, a name will be automatically calculated for the temporary file. The returned path represents the newly created transfer, which should be used to find out if the content has been successfully transferred or if the operation fails. The properties of this transfer are also returned along with the object path, to avoid a call to GetProperties. Possbile filters: Format and Fields Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Forbidden org.bluez.obex.Error.Failed array{string vcard, string name} Search(string field, string value, dict filters) Search for entries matching the given condition and return an array of vcard-listing data where every entry consists of a pair of strings containing the vcard handle and the contact name. vcard : name paired string match the search condition. field : the field in the vcard to search with { "name" (default) | "number" | "sound" } value : the string value to search for Possible filters: Order, Offset and MaxCount Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Forbidden org.bluez.obex.Error.Failed uint16 GetSize() Return the number of entries in the selected phonebook object that are actually used (i.e. indexes that correspond to non-NULL entries). Possible errors: org.bluez.obex.Error.Forbidden org.bluez.obex.Error.Failed array{string} ListFilterFields() Return All Available fields that can be used in Fields filter. Possible errors: None Filter: string Format: Items vcard format Possible values: "vcard21" (default) or "vcard30" string Order: Items order Possible values: "indexed" (default), "alphanumeric" or "phonetic" uint16 Offset: Offset of the first item, default is 0 uint16 MaxCount: Maximum number of items, default is unlimited (65535) array{string} Fields: Item vcard fields, default is all values. Possible values can be query with ListFilterFields. Synchronization hierarchy ========================= Service org.bluez.obex Interface org.bluez.obex.Synchronization1 Object path [Session object path] Methods void SetLocation(string location) Set the phonebook object store location for other operations. Should be called before all the other operations. location: Where the phonebook is stored, possible values: "int" ( "internal" which is default ) "sim1" "sim2" ...... Possible errors: org.bluez.obex.Error.InvalidArguments object, dict GetPhonebook(string targetfile) Retrieve an entire Phonebook Object store from remote device, and stores it in a local file. If an empty target file is given, a name will be automatically calculated for the temporary file. The returned path represents the newly created transfer, which should be used to find out if the content has been successfully transferred or if the operation fails. The properties of this transfer are also returned along with the object path, to avoid a call to GetProperties. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed object, dict PutPhonebook(string sourcefile) Send an entire Phonebook Object store to remote device. The returned path represents the newly created transfer, which should be used to find out if the content has been successfully transferred or if the operation fails. The properties of this transfer are also returned along with the object path, to avoid a call to GetProperties. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed Message Access hierarchy ========================= Service org.bluez.obex Interface org.bluez.obex.MessageAccess1 Object path [Session object path] Methods void SetFolder(string name) Set working directory for current session, *name* may be the directory name or '..[/dir]'. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed array{dict} ListFolders(dict filter) Returns a dictionary containing information about the current folder content. The following keys are defined: string Name : Folder name Possible filters: Offset and MaxCount Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed array{string} ListFilterFields() Return all available fields that can be used in Fields filter. Possible errors: None array{object, dict} ListMessages(string folder, dict filter) Returns an array containing the messages found in the given subfolder of the current folder, or in the current folder if folder is empty. Possible Filters: Offset, MaxCount, SubjectLength, Fields, Type, PeriodStart, PeriodEnd, Status, Recipient, Sender, Priority Each message is represented by an object path followed by a dictionary of the properties. Properties: string Subject: Message subject string Timestamp: Message timestamp string Sender: Message sender name string SenderAddress: Message sender address string ReplyTo: Message Reply-To address string Recipient: Message recipient name string RecipientAddress: Message recipient address string Type: Message type Possible values: "email", "sms-gsm", "sms-cdma" and "mms" uint64 Size: Message size in bytes boolean Text: Message text flag Specifies whether message has textual content or is binary only string Status: Message status Possible values for received messages: "complete", "fractioned", "notification" Possible values for sent messages: "delivery-success", "sending-success", "delivery-failure", "sending-failure" uint64 AttachmentSize: Message overall attachment size in bytes boolean Priority: Message priority flag boolean Read: Message read flag boolean Sent: Message sent flag boolean Protected: Message protected flag Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed void UpdateInbox(void) Request remote to update its inbox. Possible errors: org.bluez.obex.Error.Failed object, dict PushMessage(string sourcefile, string folder, dict args) Transfer a message (in bMessage format) to the remote device. The message is transferred either to the given subfolder of the current folder, or to the current folder if folder is empty. Possible args: Transparent, Retry, Charset The returned path represents the newly created transfer, which should be used to find out if the content has been successfully transferred or if the operation fails. The properties of this transfer are also returned along with the object path, to avoid a call to GetAll. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed Filter: uint16 Offset: Offset of the first item, default is 0 uint16 MaxCount: Maximum number of items, default is 1024 byte SubjectLength: Maximum length of the Subject property in the message, default is 256 array{string} Fields: Message fields, default is all values. Possible values can be query with ListFilterFields. array{string} Types: Filter messages by type. Possible values: "sms", "email", "mms". string PeriodBegin: Filter messages by starting period. Possible values: Date in "YYYYMMDDTHHMMSS" format. string PeriodEnd: Filter messages by ending period. Possible values: Date in "YYYYMMDDTHHMMSS" format. boolean Read: Filter messages by read flag. Possible values: True for read or False for unread string Recipient: Filter messages by recipient address. string Sender: Filter messages by sender address. boolean Priority: Filter messages by priority flag. Possible values: True for high priority or False for non-high priority Message hierarchy ================= Service org.bluez.obex Interface org.bluez.obex.Message1 Object path [Session object path]/{message0,...} Methods object, dict Get(string targetfile, boolean attachment) Download message and store it in the target file. If an empty target file is given, a temporary file will be automatically generated. The returned path represents the newly created transfer, which should be used to find out if the content has been successfully transferred or if the operation fails. The properties of this transfer are also returned along with the object path, to avoid a call to GetProperties. Possible errors: org.bluez.obex.Error.InvalidArguments org.bluez.obex.Error.Failed Properties string Folder [readonly] Folder which the message belongs to string Subject [readonly] Message subject string Timestamp [readonly] Message timestamp string Sender [readonly] Message sender name string SenderAddress [readonly] Message sender address string ReplyTo [readonly] Message Reply-To address string Recipient [readonly] Message recipient name string RecipientAddress [readonly] Message recipient address string Type [readonly] Message type Possible values: "email", "sms-gsm", "sms-cdma" and "mms" uint64 Size [readonly] Message size in bytes string Status [readonly] Message reception status Possible values: "complete", "fractioned" and "notification" boolean Priority [readonly] Message priority flag boolean Read [read/write] Message read flag boolean Deleted [writeonly] Message deleted flag boolean Sent [readonly] Message sent flag boolean Protected [readonly] Message protected flag bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/obex_agent.xml000066400000000000000000000005461315563672100257610ustar00rootroot00000000000000 bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/profile-api.txt000066400000000000000000000067241315563672100261000ustar00rootroot00000000000000BlueZ D-Bus Profile API description *********************************** Profile Manager hierarchy ========================= Service org.bluez Interface org.bluez.ProfileManager1 Object path /org/bluez Methods void RegisterProfile(object profile, string uuid, dict options) This registers a profile implementation. If an application disconnects from the bus all its registered profiles will be removed. HFP HS UUID: 0000111e-0000-1000-8000-00805f9b34fb Default RFCOMM channel is 6. And this requires authentication. Available options: string Name Human readable name for the profile string Service The primary service class UUID (if different from the actual profile UUID) string Role For asymmetric profiles that do not have UUIDs available to uniquely identify each side this parameter allows specifying the precise local role. Possible values: "client", "server" uint16 Channel RFCOMM channel number that is used for client and server UUIDs. If applicable it will be used in the SDP record as well. uint16 PSM PSM number that is used for client and server UUIDs. If applicable it will be used in the SDP record as well. boolean RequireAuthentication Pairing is required before connections will be established. No devices will be connected if not paired. boolean RequireAuthorization Request authorization before any connection will be established. boolean AutoConnect In case of a client UUID this will force connection of the RFCOMM or L2CAP channels when a remote device is connected. string ServiceRecord Provide a manual SDP record. uint16 Version Profile version (for SDP record) uint16 Features Profile features (for SDP record) Possible errors: org.bluez.Error.InvalidArguments org.bluez.Error.AlreadyExists void UnregisterProfile(object profile) This unregisters the profile that has been previously registered. The object path parameter must match the same value that has been used on registration. Possible errors: org.bluez.Error.DoesNotExist Profile hierarchy ================= Service unique name Interface org.bluez.Profile1 Object path freely definable Methods void Release() [noreply] This method gets called when the service daemon unregisters the profile. A profile can use it to do cleanup tasks. There is no need to unregister the profile, because when this method gets called it has already been unregistered. void NewConnection(object device, fd fd, dict fd_properties) This method gets called when a new service level connection has been made and authorized. Common fd_properties: uint16 Version Profile version (optional) uint16 Features Profile features (optional) Possible errors: org.bluez.Error.Rejected org.bluez.Error.Canceled void RequestDisconnection(object device) This method gets called when a profile gets disconnected. The file descriptor is no longer owned by the service daemon and the profile implementation needs to take care of cleaning up all connections. If multiple file descriptors are indicated via NewConnection, it is expected that all of them are disconnected before returning from this method call. Possible errors: org.bluez.Error.Rejected org.bluez.Error.Canceled bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/proximity-api.txt000066400000000000000000000034371315563672100265020ustar00rootroot00000000000000BlueZ D-Bus Proximity API description *********************************** Proximity Monitor hierarchy =========================== Service org.bluez Interface org.bluez.ProximityMonitor1 Object path [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX Properties string SignalLevel [readonly] Alert indicating that a threshold has been reached. Possible values: "unknown", "good", "regular", "weak" string LinkLossAlertLevel [readwrite] Persistent property. Sets the alert level in the proximity reporter for link loss scenario. Values: "none", "mild", "high". string ImmediateAlertLevel [readwrite] Alert level to be written in the Immediate Alert Level. Property shared between Path Loss and Find Me. Values: "none", "mild", "high". Default value is "none". Applications can disable the alert setting the value to "none". If the "Target" is not found, "none" will be emitted after the configured timeout. When changing the level, signal is the confirmation that the value was written in the remote. Proximity Reporter hierarchy =========================== Shared service used by Proximity Path Loss and Find Me. Allows per device alert level handling. Service org.bluez Interface org.bluez.ProximityReporter1 Object path [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX Properties string ImmediateAlertLevel [readonly] This property indicates that Immediate Alert Level characteristic in the local Immediate Alert Service was changed by the remote device. Property shared between Path Loss and Find Me. Values: "none", "mild", "high". string LinkLossAlertLevel [readonly] This property indicates that Alert Level characteristic in the local Link Loss Service was changed by the remote device. Values: "none", "mild", "high". bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/sap-api.txt000066400000000000000000000007001315563672100252070ustar00rootroot00000000000000BlueZ D-Bus Sim Access API description ************************************** Sim Access Profile hierarchy ============================ Service org.bluez Interface org.bluez.SimAccess1 Object path [variable prefix]/{hci0,hci1,...} Methods void Disconnect() Disconnects SAP client from the server. Possible errors: org.bluez.Error.Failed Properties boolean Connected [readonly] Indicates if SAP client is connected to the server. bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/settings-storage.txt000066400000000000000000000127731315563672100271740ustar00rootroot00000000000000BlueZ settings storage ********************** Purpose ======= The purpose of this document is to describe the directory structure of BlueZ settings storage. In effect, this document will serve as the primary, up to date source of BlueZ storage information. It is intended as reference for developers. Direct access to the storage outside from bluetoothd is highly discouraged. Adapter and remote device info are read form the storage during object initialization. Write to storage is performed immediately on every value change. Default storage directory is /var/lib/bluetooth. This can be adjusted by the --localstatedir configure switch. Default is --localstatedir=/var. All files are in ini-file format. Storage directory structure =========================== There is one directory per adapter, named by its Bluetooth address, which contains: - a settings file for the local adapter - an attributes file containing attributes of supported LE services - a cache directory containing: - one file per device, named by remote device address, which contains device name - one directory per remote device, named by remote device address, which contains: - an info file - an attributes file containing attributes of remote LE services - a ccc file containing persistent Client Characteristic Configuration (CCC) descriptor information for GATT characteristics So the directory structure is: /var/lib/bluetooth// ./settings ./attributes ./cache/ ./ ./ ... .// ./info ./attributes ./ccc .// ./info ./attributes ... Settings file format ==================== Settings file contains one [General] group with adapter info like: Alias String Friendly user provided name advertised for this adapter This value overwrites the system name (pretty hostname) Discoverable Boolean Discoverability of the adapter PairableTimeout Integer How long to stay in pairable mode before going back to non-pairable. The value is in seconds. 0 = disable timer, i.e. stay pairable forever DiscoverableTimeout Integer How long to stay in discoverable mode before going back to non-discoverable. The value is in seconds. 0 = disable timer, i.e. stay discoverable forever Sample: [General] Name=My PC Discoverable=false Pairable=true DiscoverableTimeout=0 Attributes file format ====================== The attributes file lists all attributes supported by the local adapter or remote device. Attributes are stored using their handle as group name (decimal format). Each group contains: UUID String 128-bit UUID of the attribute Value String Value of the attribute as hexadecimal encoded string EndGroupHandle Integer End group handle in decimal format Sample: [1] UUID=00002800-0000-1000-8000-00805f9b34fb Value=0018 [4] UUID=00002803-0000-1000-8000-00805f9b34fb Value=020600002A [6] UUID=00002a00-0000-1000-8000-00805f9b34fb Value=4578616D706C6520446576696365 CCC file format ====================== The ccc file stores the current CCC descriptor values for GATT characteristics which have notification/indication enabled by the remote device. Information is stored using CCC attribute handle as group name (in decimal format). Each group contains: Value String CCC descriptor value encoded in hexadecimal Cache directory file format ============================ Each file, named by remote device address, may includes multiple groups (General and ServiceRecords). In ServiceRecords, SDP records are stored using their handle as key (hexadecimal format). [General] group contains: Name String Remote device friendly name ShortName String Remote device shortened name [ServiceRecords] group contains <0x...> String SDP record as hexadecimal encoded string Info file format ================ Info file may includes multiple groups (General, Device ID, Link key and Long term key) related to a remote device. [General] group contains: Name String Remote device friendly name Alias String Alias name Class String Device class in hexadecimal, i.e. 0x000000 Appearance String Device appearance in hexadecimal, i.e. 0x0000 SupportedTechnologies List of List of technologies supported by strings device, separated by ";" Technologies can be BR/EDR or LE AddressType String An address can be "static" or "public" Trusted Boolean True if the remote device is trusted Blocked Boolean True if the remote device is blocked Services List of List of service UUIDs advertised by strings remote in 128-bits UUID format, separated by ";" [DeviceID] group contains: Source Integer Assigner of Device ID Vendor Integer Device vendor Product Integer Device product Version Integer Device version [LinkKey] group contains: Key String Key in hexadecimal format Type Integer Type of link key PINLength Integer Length of PIN [LongTermKey] group contains: Key String Long term key in hexadecimal format Authenticated Boolean True if remote device has been authenticated EncSize Integer Encrypted size EDiv Integer Encrypted diversifier Rand Integer Randomizer [SlaveLongTermKey] group contains: Same as the [LongTermKey] group, except for slave keys. bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/supported-features.txt000066400000000000000000000020031315563672100275140ustar00rootroot00000000000000Supported features in BlueZ =========================== Note that some profiles/roles will depend on external components such as oFono or ConnMan. Profile/protocol Version Role(s) --------------------------------------------------------------------------- GAP 4.0 (LE) Central, Observer, Broadcaster L2CAP 4.0 Server, Client SDP 4.0 Server, Client GATT 4.0 Server, Client SDAP 1.1 Server, Client RFCOMM 1.1 Server, Client SPP 1.1 Server, Client PXP 1.0 Reporter, Monitor HOGP 1.0 Host HTP 1.0 TIP 1.0 CSCP 1.0 Collector SAP 1.1 Server DUN 1.1 Server, Client DID 1.3 Server, Client HFP 1.5 AG, HF HSP 1.2 AG, HS GAVDTP 1.2 Source, Sink AVDTP 1.3 Source, Sink A2DP 1.3 Source, Sink AVCTP 1.3 CT, TG AVRCP 1.5 CT, TG GOEP 2.0 Client, Server FTP 1.2 Client, Server OPP 1.2 Client, Server SYNCH 1.1 Client PBAP 1.1 Client, Server MAP 1.0 Client, Server HID 1.1 Host BNEP 1.0 PAN 1.0 PANU, NAP, GN HCRP 1.2 MCAP 1.0 HDP 1.0 bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/test-coverage.txt000066400000000000000000000040341315563672100264310ustar00rootroot00000000000000BlueZ test coverage ******************* Automated unit testing ====================== Application Count Description ------------------------------------------- test-crc 9 Link Layer CRC-24 checksum test-eir 14 EIR and AD parsing test-lib 14 SDP library functions test-sdp 133 SDP qualification test cases test-uuid 30 UUID conversion handling test-mgmt 2 Management interface handling test-crypto 4 Cryptographic toolbox helpers test-textfile 4 Old textfile storage format test-ringbuf 3 Ring buffer functionality test-queue 1 Queue handling functionality test-uhid 6 Userspace HID functionality test-hfp 14 HFP Audio Gateway functionality test-avdtp 60 AVDTP qualification test cases test-avctp 9 AVCTP qualification test cases test-avrcp 92 AVRCP qualification test cases test-gobex 31 Generic OBEX functionality test-gobex-packet 9 OBEX packet handling test-gobex-header 28 OBEX header handling test-gobex-apparam 18 OBEX apparam handling test-gobex-transfer 36 OBEX transfer handling test-gdbus-client 12 D-Bus client handling ----- 519 Automated end-to-end testing ============================ Application Count Description ------------------------------------------- mgmt-tester 189 Kernel management interface testing l2cap-tester 26 Kernel L2CAP implementation testing rfcomm-tester 9 Kernel RFCOMM implementation testing smp-tester 5 Kernel SMP implementation testing sco-tester 8 Kernel SCO implementation testing gap-tester 1 Daemon D-Bus API testing hci-tester 14 Controller hardware testing ----- 252 Android end-to-end testing ========================== Application Count Description ------------------------------------------- android-tester 86 Android HAL interface testing ipc-tester 94 Android IPC resistance testing ----- 180 Android automated unit testing ============================== Application Count Description ------------------------------------------- test-ipc 14 Android IPC library functions ----- 14 bluez-tools-2.0~20170911.0.7cb788c/contrib/bluez-api-5.20-fixed/thermometer-api.txt000066400000000000000000000063761315563672100267760ustar00rootroot00000000000000BlueZ D-Bus Thermometer API description *************************************** Santiago Carot-Nemesio Health Thermometer Manager hierarchy ==================================== Service org.bluez Interface org.bluez.ThermometerManager1 Object path [variable prefix]/{hci0,hci1,...} Methods RegisterWatcher(object agent) Registers a watcher to monitor scanned measurements. This agent will be notified about final temperature measurements. Possible Errors: org.bluez.Error.InvalidArguments UnregisterWatcher(object agent) Unregisters a watcher. EnableIntermediateMeasurement(object agent) Enables intermediate measurement notifications for this agent. Intermediate measurements will be enabled only for thermometers which support it. Possible Errors: org.bluez.Error.InvalidArguments DisableIntermediateMeasurement(object agent) Disables intermediate measurement notifications for this agent. It will disable notifications in thermometers when the last agent removes the watcher for intermediate measurements. Possible Errors: org.bluez.Error.InvalidArguments org.bluez.Error.NotFound Health Thermometer Profile hierarchy ==================================== Service org.bluez Interface org.bluez.Thermometer1 Object path [variable prefix]/{hci0,hci1,...}/dev_XX_XX_XX_XX_XX_XX Properties boolean Intermediate [readonly] True if the thermometer supports intermediate measurement notifications. uint16 Interval (optional) [readwrite] The Measurement Interval defines the time (in seconds) between measurements. This interval is not related to the intermediate measurements and must be defined into a valid range. Setting it to zero means that no periodic measurements will be taken. uint16 Maximum (optional) [readonly] Defines the maximum value allowed for the interval between periodic measurements. uint16 Minimum (optional) [readonly] Defines the minimum value allowed for the interval between periodic measurements. Health Thermometer Watcher hierarchy ==================================== Service unique name Interface org.bluez.ThermometerWatcher1 Object path freely definable Methods void MeasurementReceived(dict measurement) This callback gets called when a measurement has been scanned in the thermometer. Measurement: int16 Exponent: int32 Mantissa: Exponent and Mantissa values as extracted from float value defined by IEEE-11073-20601. Measurement value is calculated as (Mantissa) * (10^Exponent) For special cases Exponent is set to 0 and Mantissa is set to one of following values: +(2^23 - 1) NaN (invalid or missing data) -(2^23) NRes +(2^23 - 2) +Infinity -(2^23 - 2) -Infinity string Unit: Possible values: "celsius" or "fahrenheit" uint64 Time (optional): Time of measurement, if supported by device. Expressed in seconds since epoch. string Type (optional): Only present if measurement type is known. Possible values: "armpit", "body", "ear", "finger", "intestines", "mouth", "rectum", "toe", "tympanum" string Measurement: Possible values: "final" or "intermediate" bluez-tools-2.0~20170911.0.7cb788c/contrib/build-mans.sh000077500000000000000000000013731315563672100221460ustar00rootroot00000000000000#!/bin/sh pod2man -n bt-adapter -c "bluez-tools" -r "" man/bt-adapter.pod > ../src/bt-adapter.1 pod2man -n bt-agent -c "bluez-tools" -r "" man/bt-agent.pod > ../src/bt-agent.1 pod2man -n bt-device -c "bluez-tools" -r "" man/bt-device.pod > ../src/bt-device.1 # pod2man -n bt-monitor -c "bluez-tools" -r "" man/bt-monitor.pod > ../src/bt-monitor.1 # pod2man -n bt-audio -c "bluez-tools" -r "" man/bt-audio.pod > ../src/bt-audio.1 # pod2man -n bt-input -c "bluez-tools" -r "" man/bt-input.pod > ../src/bt-input.1 pod2man -n bt-network -c "bluez-tools" -r "" man/bt-network.pod > ../src/bt-network.1 # pod2man -n bt-serial -c "bluez-tools" -r "" man/bt-serial.pod > ../src/bt-serial.1 pod2man -n bt-obex -c "bluez-tools" -r "" man/bt-obex.pod > ../src/bt-obex.1 bluez-tools-2.0~20170911.0.7cb788c/contrib/gen-dbus-gobject.pl000077500000000000000000001126521315563672100232360ustar00rootroot00000000000000#!/usr/bin/perl -w # # bluez-tools - a set of tools to manage bluetooth devices for linux # # Copyright (C) 2010 Alexander Orlenko # # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA # use strict; die "usage: -header|source FILE \n" unless $ARGV[0] && $ARGV[1] && $ARGV[0] =~ /^-(header|source)$/; sub parse_doc_api { my ($doc_api_file, $hierarchy_id) = @_; $hierarchy_id = 1 unless defined $hierarchy_id && $hierarchy_id > 0; my %data; open INPUT, "<$doc_api_file" or die "Can't open '$doc_api_file': $!\n"; my $n = 0; my $hierarchy_n = 0; my $section = ''; while() { $n++; s/\s+$//; if ($n == 1) { if (/^BlueZ D-Bus (\S+\s{1})+API description$/) { $data{'api'} = 'BlueZ'; $data{'dbus_conn'} = 'system_conn'; } elsif (/^obex.*?API description$/i) { $data{'api'} = 'Obex'; $data{'dbus_conn'} = 'session_conn'; } elsif (/^Cycling Speed and Cadence API description$/) { $data{'api'} = 'Cycling Speed'; $data{'dbus_conn'} = 'system_conn'; } elsif (/^Heart Rate API description$/) { $data{'api'} = 'Heart Rate'; $data{'dbus_conn'} = 'system_conn'; } else { die "invalid file format (1)\n"; } next; } /^\s*$/ && next; if (/^(.+) hierarchy$/) { my $hierarchy = $1; $section = 'hierarchy'; $hierarchy_n++; my $dbus_conn = $data{'dbus_conn'}; undef %data if $hierarchy_n == $hierarchy_id; last if $hierarchy_n == $hierarchy_id+1; $data{'hierarchy'} = $hierarchy; $data{'dbus_conn'} = $dbus_conn; } elsif (/^Service\s*(.+)$/) { my $service = $1; # Remove strings surrounded by brackets and parentheses $service =~ s/\s*((\(|\[|\{).*(\)|\]|\}))\s*//; die "invalid file format (2)\n" unless $section eq 'hierarchy'; if($service eq 'org.bluez' || $service eq 'org.bluez.obex') { $data{'serviceName'} = $service; } elsif ($service eq 'unique name') { # $data{'serviceName'} = undef; die "invalid service: User defined DBus object. Please create manually.\n"; } else { die "invalid service: $service\n"; } } elsif (/^Interface\s*(.+)$/) { my $intf = $1; # Remove everything after the whitespace $intf =~ s/\s+.*//; die "invalid file format (3)\n" unless $section eq 'hierarchy'; die "invalid interface: $intf\n" unless $intf =~ /^org\.bluez\./; $data{'intf'} = $intf; $data{$intf} = undef; $data{$intf}{'methods'} = undef; $data{$intf}{'signals'} = undef; $data{$intf}{'properties'} = undef; } elsif (/^Object path\s*(.+)/) { my $obj_path = $1; die "invalid file format (4)\n" unless $section eq 'hierarchy'; if($obj_path =~ /^freely definable/ || $obj_path =~ /^\[.*\]/ || $obj_path =~ /\{.*\}/ || $obj_path =~ /dev_XX_XX_XX_XX_XX_XX/) { $data{'objectPath'} = undef; } else { $data{'objectPath'} = $obj_path if $obj_path =~ /^[A-Za-z0-9\/]+$/; } } elsif (/^Object name\s*(.+)/) { my $obj_name = $1; die "invalid file format (4)\n" unless $section eq 'hierarchy'; $data{'objectName'} = $obj_name if $obj_name =~ /^[A-Za-z]+$/; } elsif (/^Methods/) { die "invalid file format (5)\n" unless $section eq 'hierarchy'; $section = 'methods'; s/Methods/ /; } elsif (/^Signals/) { # Disabled for now. Some APIs do not have methods. # die "invalid file format (6)\n" unless $section eq 'methods'; $section = 'signals'; s/Signals/ /; } elsif(/^Properties/) { # Disabled for now. Some APIs do not have methods or signals. # die "invalid file format (7)\n" unless $section eq 'signals' || $section eq 'methods'; $section = 'properties'; s/Properties/ /; } elsif(/^Filter/) { $section = 'filter'; s/Filter/ /; } if (defined $section && $section eq 'methods' && /^\s+((\S+) (\w+)\((.*)\)( \[(\w+)\])?)$/) { my $decl = $1; my $ret = $2; my $name = $3; my $args = $4; my $flag = $6; # Check for void parameters if(lc($args) eq 'void') { $args = ''; } $data{$data{'intf'}}{'methods'}{$name}{'decl'} = $decl; $data{$data{'intf'}}{'methods'}{$name}{'ret'} = $ret; $data{$data{'intf'}}{'methods'}{$name}{'flag'} = $flag; @{$data{$data{'intf'}}{'methods'}{$name}{'args'}} = map {type => (split / /, $_)[0], name => (split / /, $_)[1]}, (split /, /, $args); } elsif (defined $section && $section eq 'signals' && /^\s+((\w+)\((.*)\))$/) { my $decl = $1; my $name = $2; my $args = $3; $data{$data{'intf'}}{'signals'}{$name}{'decl'} = $decl; @{$data{$data{'intf'}}{'signals'}{$name}{'args'}} = map {type => (split / /, $_)[0], name => (split / /, $_)[1]}, (split /, /, $args); } elsif (defined $section && $section eq 'properties' && /^\s+((\S+) (\w+) \[(readonly|writeonly|readwrite|read\/write).*\])$/) { my $decl = $1; my $type = $2; my $name = $3; my $mode = $4; my $optional = 0; if ($decl =~ /\(optional\)/i or $decl =~ /\[.*optional\]/i) { $optional = 1; } $data{$data{'intf'}}{'properties'}{$name}{'decl'} = $decl; $data{$data{'intf'}}{'properties'}{$name}{'type'} = $type; $data{$data{'intf'}}{'properties'}{$name}{'mode'} = $mode; $data{$data{'intf'}}{'properties'}{$name}{'optional'} = $optional; } elsif (defined $section && $section eq 'filter' && /^\s+((\S+) (\w+)):$/) { my $decl = $1; my $type = $2; my $name = $3; $data{$data{'intf'}}{'filter'}{$name}{'decl'} = $decl; $data{$data{'intf'}}{'filter'}{$name}{'type'} = $type; } } return \%data; } my $HEADER = < * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ EOH sub get_g_type { my $obj_type = shift; my $g_type; $g_type = 'void ' if $obj_type eq 'void'; $g_type = 'gchar *' if $obj_type eq 'object' || $obj_type eq 'string'; # $g_type = 'GHashTable *' if $obj_type =~ /^dict/; # May be used later... $g_type = 'GVariant *' if $obj_type =~ /^dict/; # GVariant dictionary $g_type = 'GVariant *' if $obj_type eq 'variant'; $g_type = 'guint8 ' if $obj_type eq 'uint8' || $obj_type eq 'byte'; $g_type = 'gboolean ' if $obj_type eq 'boolean'; $g_type = 'gint16 ' if $obj_type eq 'int16'; $g_type = 'guint16 ' if $obj_type eq 'uint16'; $g_type = 'gint32 ' if $obj_type eq 'int32'; $g_type = 'guint32 ' if $obj_type eq 'uint32' || $obj_type eq 'fd'; $g_type = 'guint64 ' if $obj_type eq 'uint64'; # $g_type = 'GPtrArray *' if $obj_type eq 'array{object}' || $obj_type eq 'array{dict}'; $g_type = 'gchar **' if $obj_type eq 'array{object}'; $g_type = 'GVariant *' if $obj_type eq 'array{dict}'; $g_type = 'gchar **' if $obj_type eq 'array{string}'; $g_type = 'guint8 *' if $obj_type eq 'array{byte}'; die "unknown object type (1): $obj_type\n" unless defined $g_type; return $g_type; } sub get_default_value { my $c_type = shift; my $default_value; $default_value = '0x0'; $default_value = 'NULL' if $c_type =~ /\*$/; $default_value = 'FALSE' if $c_type =~ /boolean/; $default_value = '0' if $c_type =~ /int/; die "unknown C type (3): $c_type\n" unless defined $default_value; return $default_value; } sub is_const_type { my $obj_type = shift; if($obj_type eq 'object' || $obj_type eq 'string' || $obj_type eq 'array{object}' || $obj_type eq 'array{string}') { return 1; } else { return 0; } } sub get_g_variant_format_char { my $obj_type = shift; my $g_variant_type; $g_variant_type = 'o' if $obj_type eq 'object'; $g_variant_type = 's' if $obj_type eq 'string'; $g_variant_type = '@a{sv}' if $obj_type =~ /^dict/; $g_variant_type = 'v' if $obj_type eq 'variant'; $g_variant_type = 'y' if $obj_type eq 'uint8' || $obj_type eq 'byte'; $g_variant_type = 'b' if $obj_type eq 'boolean'; $g_variant_type = 'n' if $obj_type eq 'int16'; $g_variant_type = 'q' if $obj_type eq 'uint16'; $g_variant_type = 'h' if $obj_type eq 'int32' || $obj_type eq 'fd'; $g_variant_type = 'u' if $obj_type eq 'uint32'; $g_variant_type = 't' if $obj_type eq 'uint64'; $g_variant_type = '@ao' if $obj_type eq 'array{object}'; # $g_variant_type = 'a&v' if $obj_type eq 'array{dict}'; $g_variant_type = '@as' if $obj_type eq 'array{string}'; $g_variant_type = '@ay' if $obj_type eq 'array{byte}'; die "unknown object type (1): $obj_type\n" unless defined $g_variant_type; return $g_variant_type; } sub generate_g_variant_params { my @params = @{$_[0]}; my $variant; # Size greater than 0? die "Too few arguments\n" unless @params > 0; $variant = 'g_variant_new ('; $variant .= '"('; foreach(@params) { $variant .= get_g_variant_format_char($_->{'type'}); } $variant .= ')", '; for (my $i=0; $i < @params; $i++) { $variant .= '(guint64) ' if $params[$i]{'type'} eq 'uint64'; $variant .= '(gint64) ' if $params[$i]{'type'} eq 'int64'; $variant .= $params[$i]{'name'}; $variant .= ', ' unless $i == (@params - 1); } $variant .= ')'; return $variant; } sub generate_header { my $node = shift; my $HEADER_TEMPLATE = < {DBUS_OBJECT_DEFS} /* * Type macros */ #define {\$OBJECT}_TYPE ({\$object}_get_type()) #define {\$OBJECT}(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), {\$OBJECT}_TYPE, {\$Object})) #define {\$OBJECT}_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), {\$OBJECT}_TYPE)) #define {\$OBJECT}_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), {\$OBJECT}_TYPE, {\$Object}Class)) #define {\$OBJECT}_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), {\$OBJECT}_TYPE)) #define {\$OBJECT}_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), {\$OBJECT}_TYPE, {\$Object}Class)) typedef struct _{\$Object} {\$Object}; typedef struct _{\$Object}Class {\$Object}Class; typedef struct _{\$Object}Private {\$Object}Private; struct _{\$Object} { GObject parent_instance; /*< private >*/ {\$Object}Private *priv; }; struct _{\$Object}Class { GObjectClass parent_class; }; /* used by {\$OBJECT}_TYPE */ GType {\$object}_get_type(void) G_GNUC_CONST; /* * Constructor */ {CONSTRUCTOR_DEFS} {IF_METHODS} /* * Method definitions */ {FI_METHODS} {METHOD_DEFS} #ifdef __cplusplus } #endif #endif /* __{\$OBJECT}_H */ EOT my $intf = $node->{'intf'}; my $obj = exists $node->{'objectName'} ? $node->{'objectName'} : (split /\./, $intf)[-1]; # Because the BlueZ 5 API uses version numbers at the end of the interfaces, trim off the version number $obj =~ s/\d+$//; # TODO: In the future, when BlueZ 5 includes mutiple versions of the same interface, we should distinguish them. # Prefix the Obex API calls to avoid conflicts with the BlueZ API $obj = "Obex".$obj if $intf =~ /obex/i; # TODO: In the future, when BlueZ 5 includes mutiple versions of the same interface, we should distinguish them. my $obj_lc = lc join('_', $obj =~ /([A-Z]+[a-z]*)/g); my $obj_uc = uc join('_', $obj =~ /([A-Z]+[a-z]*)/g); # Prefix the Obex API calls to avoid conflicts with the BlueZ API my $dbus_object_defs = ""; $dbus_object_defs .= "#define {\$OBJECT}_DBUS_SERVICE \"$node->{'serviceName'}\"\n" if defined $node->{'serviceName'}; $dbus_object_defs .= "#define {\$OBJECT}_DBUS_INTERFACE \"$node->{'intf'}\"\n"; $dbus_object_defs .= "#define {\$OBJECT}_DBUS_PATH \"$node->{'objectPath'}\"\n" if defined $node->{'objectPath'}; my $constructor_defs = "{\$Object} *{\$object}_new("; my $constructor_args = ""; if(not exists $node->{'objectPath'} or not defined $node->{'objectPath'}) { $constructor_args .= ", " if length($constructor_args) > 0; $constructor_args .= "const gchar *dbus_object_path" } $constructor_defs .= $constructor_args; $constructor_defs .= ");\n"; my $method_defs = ""; $method_defs .= "const gchar *{\$object}_get_dbus_object_path({\$Object} *self);\n" unless defined $node->{'objectPath'}; $method_defs .= "\n" if length($method_defs) > 0; for my $method (sort keys %{$node->{$intf}{'methods'}}) { my @a = $method =~ /([A-Z]+[a-z]*)/g; my %m = %{$node->{$intf}{'methods'}{$method}}; my $in_args = join ', ', (map "const ".get_g_type($_->{'type'}).$_->{'name'}, @{$m{'args'}}); $method_defs .= (is_const_type($m{'ret'}) eq 1 ? "const " : "").get_g_type($m{'ret'})."{\$object}_".(join '_', (map lc $_, @a))."({\$Object} *self, ". ($in_args eq '' ? "" : "$in_args, ")."GError **error);\n"; } $method_defs .= "\n" if %{$node->{$intf}{'methods'}}; # Add Properties interface definitions if(keys(%{$node->{$intf}{'properties'}}) > 0) { $method_defs .= "GVariant *{\$object}_get_properties({\$Object} *self, GError **error);\n"; $method_defs .= "void {\$object}_set_property({\$Object} *self, const gchar *name, const GVariant *value, GError **error);\n"; $method_defs .= "\n"; } for my $property (sort keys %{$node->{$intf}{'properties'}}) { my @a = $property =~ /([A-Z]+[a-z]*)/g; my %p = %{$node->{$intf}{'properties'}{$property}}; # If the property is named 'Type', rename it to something else as it will conflict with GLib's 'Type' property if($property =~ /^type$/i) { my @i_name = $obj =~ /([A-Z]+[a-z]*)/g; my @new_name = ($i_name[-1], @a); $method_defs .= "// This has been renamed because '{\$object}_get_type' is already used by GLib\n"; if ($p{'mode'} eq 'readwrite' or $p{'mode'} eq 'readonly' or $p{'mode'} eq 'read/write') { $method_defs .= (is_const_type($p{'type'}) eq 1 ? "const " : "").get_g_type($p{'type'})."{\$object}_get_".(join '_', (map lc $_, @new_name))."({\$Object} *self, GError **error);\n"; } if ($p{'mode'} eq 'readwrite' or $p{'mode'} eq 'writeonly' or $p{'mode'} eq 'read/write') { $method_defs .= "void {\$object}_set_".(join '_', (map lc $_, @new_name))."({\$Object} *self, const ".get_g_type($p{'type'})."value, GError **error);\n"; } } else { if ($p{'mode'} eq 'readwrite' or $p{'mode'} eq 'readonly' or $p{'mode'} eq 'read/write') { $method_defs .= (is_const_type($p{'type'}) eq 1 ? "const " : "").get_g_type($p{'type'})."{\$object}_get_".(join '_', (map lc $_, @a))."({\$Object} *self, GError **error);\n"; } if ($p{'mode'} eq 'readwrite' or $p{'mode'} eq 'writeonly' or $p{'mode'} eq 'read/write') { $method_defs .= "void {\$object}_set_".(join '_', (map lc $_, @a))."({\$Object} *self, const ".get_g_type($p{'type'})."value, GError **error);\n"; } } } $method_defs =~ s/\s+$//s; my $output = "$HEADER\n$HEADER_TEMPLATE\n"; $output =~ s/{DBUS_OBJECT_DEFS}/$dbus_object_defs/; $output =~ s/{CONSTRUCTOR_DEFS}/$constructor_defs/; if (scalar keys %{$node->{$intf}{'methods'}} > 0 or scalar keys %{$node->{$intf}{'properties'}} > 0) { $output =~ s/\{IF_METHODS\}\s+(.+?)\s+\{FI_METHODS\}/$1/gs; } else { $output =~ s/\s+\{IF_METHODS\}.+?\{FI_METHODS\}//gs; } $output =~ s/{METHOD_DEFS}/$method_defs/; $output =~ s/{\$OBJECT}/$obj_uc/g; $output =~ s/{\$Object}/$obj/g; $output =~ s/{\$object}/$obj_lc/g; return $output; } sub generate_source { my $node = shift; my $SOURCE_TEMPLATE = < #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "{\$object}.h" #define {\$OBJECT}_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), {\$OBJECT}_TYPE, {\$Object}Private)) struct _{\$Object}Private { GDBusProxy *proxy; {IF_PROPERTIES} Properties *properties; {FI_PROPERTIES} {IF_NO_OBJECT_PATH} gchar *object_path; {FI_NO_OBJECT_PATH} }; G_DEFINE_TYPE_WITH_PRIVATE({\$Object}, {\$object}, G_TYPE_OBJECT); enum { PROP_0, {CONSTRUCTOR_PROPERTIES} }; static void _{\$object}_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _{\$object}_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _{\$object}_create_gdbus_proxy({\$Object} *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void {\$object}_dispose(GObject *gobject) { {\$Object} *self = {\$OBJECT}(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); {IF_PROPERTIES_EXT} /* Properties free */ g_clear_object(&self->priv->properties); {FI_PROPERTIES_EXT} {IF_NO_OBJECT_PATH} /* Object path free */ g_free(self->priv->object_path); {FI_NO_OBJECT_PATH} /* Chain up to the parent class */ G_OBJECT_CLASS({\$object}_parent_class)->dispose(gobject); } static void {\$object}_finalize (GObject *gobject) { {\$Object} *self = {\$OBJECT}(gobject); G_OBJECT_CLASS({\$object}_parent_class)->finalize(gobject); } static void {\$object}_class_init({\$Object}Class *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = {\$object}_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _{\$object}_get_property; gobject_class->set_property = _{\$object}_set_property; {IF_NO_OBJECT_PATH} /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "{\$Object} D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); {FI_NO_OBJECT_PATH} if (pspec) g_param_spec_unref(pspec); } static void {\$object}_init({\$Object} *self) { self->priv = {\$object}_get_instance_private (self); self->priv->proxy = NULL; {IF_PROPERTIES} self->priv->properties = NULL; {FI_PROPERTIES} {IF_NO_OBJECT_PATH} self->priv->object_path = NULL; {FI_NO_OBJECT_PATH} g_assert({\$conn} != NULL); {CONSTRUCTOR_CALL} } static void _{\$object}_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { {\$Object} *self = {\$OBJECT}(object); switch (property_id) { {CONSTRUCTOR_GETTERS} default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _{\$object}_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { {\$Object} *self = {\$OBJECT}(object); GError *error = NULL; switch (property_id) { {CONSTRUCTOR_SETTERS} default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ {CONSTRUCTOR} /* Private DBus proxy creation */ static void _{\$object}_create_gdbus_proxy({\$Object} *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert({\$OBJECT}_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync({\$conn}, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, {\$OBJECT}_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; {IF_PROPERTIES} self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", {\$dbus_type}, "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); {FI_PROPERTIES} } {IF_METHODS} /* Methods */ {FI_METHODS} {IF_NO_OBJECT_PATH} /* Get DBus object path */ const gchar *{\$object}_get_dbus_object_path({\$Object} *self) { g_assert({\$OBJECT}_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } {FI_NO_OBJECT_PATH} {METHODS} {IF_PROPERTIES} /* Properties access methods */ {PROPERTIES_ACCESS_METHODS} {FI_PROPERTIES} EOT my $intf = $node->{'intf'}; my $obj = exists $node->{'objectName'} ? $node->{'objectName'} : (split /\./, $intf)[-1]; # Prefix the Obex API calls to avoid conflicts with the BlueZ API $obj = "Obex".$obj if $intf =~ /obex/i; # Because the BlueZ 5 API uses version numbers at the end of the interfaces, trim off the version number $obj =~ s/\d+$//; # TODO: In the future, when BlueZ 5 includes mutiple versions of the same interface, we should distinguish them. my $obj_lc = lc join('_', $obj =~ /([A-Z]+[a-z]*)/g); my $obj_uc = uc join('_', $obj =~ /([A-Z]+[a-z]*)/g); my $constructor_properties = ""; if(not exists $node->{'objectPath'} or not defined $node->{'objectPath'}) { $constructor_properties .= "\tPROP_DBUS_OBJECT_PATH"; $constructor_properties .= " /* readwrite, construct only */\n"; } my $constructor_call = ""; if(exists $node->{'serviceName'} and defined $node->{'serviceName'} and exists $node->{'objectPath'} and defined $node->{'objectPath'}) { $constructor_call .= "\tGError *error = NULL;\n". "\t_{\$object}_create_gdbus_proxy(self, {\$OBJECT}_DBUS_SERVICE, {\$OBJECT}_DBUS_PATH, &error);\n". "\tg_assert(error == NULL);\n"; } my $constructor_getters = ""; if(not exists $node->{'objectPath'} or not defined $node->{'objectPath'}) { $constructor_getters .= "\tcase PROP_DBUS_OBJECT_PATH:\n"; $constructor_getters .= "\t\tg_value_set_string(value, {\$object}_get_dbus_object_path(self));\n"; $constructor_getters .= "\t\tbreak;\n"; } my $constructor_setters = ""; if(not exists $node->{'objectPath'} or not defined $node->{'objectPath'}) { $constructor_setters .= "\tcase PROP_DBUS_OBJECT_PATH:\n". "\t\tself->priv->object_path = g_value_dup_string(value);\n"; $constructor_setters .= "\t\t_{\$object}_create_gdbus_proxy(self, {\$OBJECT}_DBUS_SERVICE, self->priv->object_path, &error);\n"; $constructor_setters .= "\t\tbreak;\n"; } my $constructor_def = "{\$Object} *{\$object}_new("; my $constructor_args = ""; if(not exists $node->{'objectPath'} or not defined $node->{'objectPath'}) { $constructor_args .= ", " if length($constructor_args) > 0; $constructor_args .= "const gchar *dbus_object_path" } $constructor_def .= $constructor_args; $constructor_def .= ")\n". "{\n". "\treturn g_object_new({\$OBJECT}_TYPE, "; if(not exists $node->{'objectPath'} or not defined $node->{'objectPath'}) { $constructor_def .= "\"DBusObjectPath\", dbus_object_path, "; } $constructor_def .= "NULL);\n". "}\n"; my $dbus_type = "NULL"; if(exists $node->{'dbus_conn'} and defined $node->{'dbus_conn'}) { $dbus_type = "\"system\"" if $node->{'dbus_conn'} eq 'system_conn'; $dbus_type = "\"session\"" if $node->{'dbus_conn'} eq 'session_conn'; } else { die '$node->{\'dbus_conn\'} is undefined!'; } my $methods = ""; for my $method (sort keys %{$node->{$intf}{'methods'}}) { my @a = $method =~ /([A-Z]+[a-z]*)/g; my %m = %{$node->{$intf}{'methods'}{$method}}; my $in_args = join ', ', (map "const ".get_g_type($_->{'type'}).$_->{'name'}, @{$m{'args'}}); my $method_def = (is_const_type($m{'ret'}) eq 1 ? "const " : "").get_g_type($m{'ret'})."{\$object}_".(join '_', (map lc $_, @a))."({\$Object} *self, ". ($in_args eq '' ? "" : "$in_args, ")."GError **error)"; $methods .= "/* $m{'decl'} */\n". "$method_def\n". "{\n". "\tg_assert({\$OBJECT}_IS(self));\n"; if($m{'ret'} eq 'void') { $methods .= "\tg_dbus_proxy_call_sync(self->priv->proxy, \"$method\", ".($in_args eq '' ? "NULL" : generate_g_variant_params($m{'args'})).", G_DBUS_CALL_FLAGS_NONE, -1, NULL, error);\n"; } else { $methods .= "\t".(is_const_type($m{'ret'}) eq 1 ? "const " : "").get_g_type($m{'ret'})."ret = ".get_default_value(get_g_type($m{'ret'})).";\n". "\tGVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, \"$method\", ".($in_args eq '' ? "NULL" : generate_g_variant_params($m{'args'})).", G_DBUS_CALL_FLAGS_NONE, -1, NULL, error);\n". "\tif (proxy_ret != NULL)\n". "\t\treturn ".get_default_value(get_g_type($m{'ret'})).";\n". "\tproxy_ret = g_variant_get_child_value(proxy_ret, 0);\n"; if($m{'ret'} eq 'boolean') { $methods .= "\tret = g_variant_get_boolean(proxy_ret);\n"; } elsif($m{'ret'} eq 'byte') { $methods .= "\tret = g_variant_get_byte(proxy_ret);\n"; } elsif($m{'ret'} eq 'int8') { $methods .= "\tret = (gint8) g_variant_get_byte(proxy_ret);\n"; } elsif($m{'ret'} eq 'uint8') { $methods .= "\tret = (guint8) g_variant_get_byte(proxy_ret);\n"; } elsif($m{'ret'} eq 'int16') { $methods .= "\tret = g_variant_get_int16(proxy_ret);\n"; } elsif($m{'ret'} eq 'uint16') { $methods .= "\tret = g_variant_get_uint16(proxy_ret);\n"; } elsif($m{'ret'} eq 'int32') { $methods .= "\tret = g_variant_get_int32(proxy_ret);\n"; } elsif($m{'ret'} eq 'uint32') { $methods .= "\tret = g_variant_get_uint32(proxy_ret);\n"; } elsif($m{'ret'} eq 'fd') { $methods .= "\tret = g_variant_get_uint32(proxy_ret);\n"; } elsif($m{'ret'} eq 'int64') { $methods .= "\tret = g_variant_get_int64(proxy_ret);\n"; } elsif($m{'ret'} eq 'uint64') { $methods .= "\tret = g_variant_get_uint64(proxy_ret);\n"; } elsif($m{'ret'} eq 'float' || $m{'ret'} eq 'double') { $methods .= "\tret = g_variant_get_double(proxy_ret);\n"; } elsif($m{'ret'} eq 'object' || $m{'ret'} eq 'string') { $methods .= "\tret = g_variant_get_string(proxy_ret, NULL);\n"; } elsif($m{'ret'} eq 'variant') { $methods .= "\tret = g_variant_get_variant(proxy_ret);\n"; } elsif($m{'ret'} eq 'array{string}') { $methods .= "\tret = g_variant_get_strv(proxy_ret, NULL);\n"; } elsif($m{'ret'} eq 'array{object}') { $methods .= "\tret = g_variant_get_objv(proxy_ret, NULL);\n"; } elsif($m{'ret'} eq 'array{byte}') { $methods .= "\tret = (guint8 *) g_variant_get_fixed_array(proxy_ret, NULL, sizeof(guint8));\n"; } else { # die "Unknown method return type: $m{'ret'}\n"; # Assume this is an array of variants or dictionaries or something else $methods .= "\tret = g_variant_ref_sink(proxy_ret);\n"; } $methods .= "\tg_variant_unref(proxy_ret);\n". "\treturn ret;\n"; } $methods .= "}\n\n"; } $methods =~ s/\s+$//s; my $properties_access_methods = ""; if(keys(%{$node->{$intf}{'properties'}}) > 0) { $properties_access_methods .= "GVariant *{\$object}_get_properties({\$Object} *self, GError **error)\n". "{\n". "\tg_assert({\$OBJECT}_IS(self));\n". "\tg_assert(self->priv->properties != NULL);\n". "\treturn properties_get_all(self->priv->properties, {\$OBJECT}_DBUS_INTERFACE, error);\n". "}\n". "\n". "void {\$object}_set_property({\$Object} *self, const gchar *name, const GVariant *value, GError **error)\n". "{\n". "\tg_assert({\$OBJECT}_IS(self));\n". "\tg_assert(self->priv->properties != NULL);\n". "\tproperties_set(self->priv->properties, {\$OBJECT}_DBUS_INTERFACE, name, value, error);\n". "}\n". "\n"; } for my $property (sort keys %{$node->{$intf}{'properties'}}) { my @a = $property =~ /([A-Z]+[a-z]*)/g; my %p = %{$node->{$intf}{'properties'}{$property}}; # my $property_var = join '_', (map lc $_, @a); my $property_var = ''; # If the property is named 'Type', rename it to something else as it will conflict with GLib's 'Type' property if($property =~ /^type$/i) { my @i_name = $obj =~ /([A-Z]+[a-z]*)/g; my @new_name = ($i_name[-1], @a); $property_var = join '_', (map lc $_, @new_name); } else { $property_var = join '_', (map lc $_, @a); } my $enum = "PROP_".(join '_', (map uc $_, @a)); my $property_get_method = "{\$object}_get_$property_var"; my $property_set_method = "{\$object}_set_$property_var"; if ($p{'mode'} eq 'readwrite' or $p{'mode'} eq 'readonly' or $p{'mode'} eq 'read/write') { $properties_access_methods .= (is_const_type($p{'type'}) eq 1 ? "const " : "").get_g_type($p{'type'})."$property_get_method({\$Object} *self, GError **error)\n". "{\n". "\tg_assert({\$OBJECT}_IS(self));\n". "\tg_assert(self->priv->properties != NULL);\n". "\tGVariant *prop = properties_get(self->priv->properties, {\$OBJECT}_DBUS_INTERFACE, \"$property\", error);\n". "\tif(prop == NULL)\n". "\t\treturn ".get_default_value(get_g_type($p{'type'})).";\n"; if($p{'type'} eq 'boolean') { $properties_access_methods .= "\tgboolean ret = g_variant_get_boolean(prop);\n"; } elsif($p{'type'} eq 'byte') { $properties_access_methods .= "\tguchar ret = g_variant_get_byte(prop);\n"; } elsif($p{'type'} eq 'int8') { $properties_access_methods .= "\tgint8 ret = g_variant_get_byte(prop);\n"; } elsif($p{'type'} eq 'uint8') { $properties_access_methods .= "\tguint8 ret = g_variant_get_byte(prop);\n"; } elsif($p{'type'} eq 'int16') { $properties_access_methods .= "\tgint16 ret = g_variant_get_int16(prop);\n"; } elsif($p{'type'} eq 'uint16') { $properties_access_methods .= "\tguint16 ret = g_variant_get_uint16(prop);\n"; } elsif($p{'type'} eq 'int32') { $properties_access_methods .= "\tgint32 ret = g_variant_get_int32(prop);\n"; } elsif($p{'type'} eq 'uint32') { $properties_access_methods .= "\tguint32 ret = g_variant_get_uint32(prop);\n"; } elsif($p{'type'} eq 'fd') { $properties_access_methods .= "\tguint32 ret = g_variant_get_uint32(prop);\n"; } elsif($p{'type'} eq 'int64') { $properties_access_methods .= "\tgint64 ret = g_variant_get_int64(prop);\n"; } elsif($p{'type'} eq 'uint64') { $properties_access_methods .= "\tguint64 ret = g_variant_get_uint64(prop);\n"; } elsif($p{'type'} eq 'float' || $p{'type'} eq 'double') { $properties_access_methods .= "\tgdouble ret = g_variant_get_double(prop);\n"; } elsif($p{'type'} eq 'object' || $p{'type'} eq 'string') { $properties_access_methods .= "\tconst gchar *ret = g_variant_get_string(prop, NULL);\n"; } elsif($p{'type'} eq 'variant') { $properties_access_methods .= "\tGVariant *ret = g_variant_get_variant(prop);\n"; } elsif($p{'type'} eq 'array{string}') { $properties_access_methods .= "\tconst gchar **ret = g_variant_get_strv(prop, NULL);\n"; } elsif($p{'type'} eq 'array{object}') { $properties_access_methods .= "\tconst gchar **ret = g_variant_get_objv(prop, NULL);\n"; } elsif($p{'type'} eq 'array{byte}') { $properties_access_methods .= "\tguint8 *ret = (guint8 *) g_variant_get_fixed_array(prop, NULL, sizeof(guint8));\n"; } else { # die "Unknown property return type: $p{'type'}\n"; # Assume this is an array of variants or dictionaries or something else $properties_access_methods .= "\tGVariant *ret = g_variant_ref_sink(prop);\n"; } $properties_access_methods .= "\tg_variant_unref(prop);\n". "\treturn ret;\n". "}\n\n"; } if ($p{'mode'} eq 'readwrite' or $p{'mode'} eq 'writeonly' or $p{'mode'} eq 'read/write') { $properties_access_methods .= "void $property_set_method({\$Object} *self, const ".get_g_type($p{'type'})."value, GError **error)\n". "{\n". "\tg_assert({\$OBJECT}_IS(self));\n". "\tg_assert(self->priv->properties != NULL);\n". "\tproperties_set(self->priv->properties, {\$OBJECT}_DBUS_INTERFACE, \"$property\", "; if($p{'type'} eq 'boolean') { $properties_access_methods .= "g_variant_new_boolean(value)"; } elsif($p{'type'} eq 'byte') { $properties_access_methods .= "g_variant_new_byte(value)"; } elsif($p{'type'} eq 'uint8') { $properties_access_methods .= "g_variant_new_byte(value)"; } elsif($p{'type'} eq 'int16') { $properties_access_methods .= "g_variant_new_int16(value)"; } elsif($p{'type'} eq 'uint16') { $properties_access_methods .= "g_variant_new_uint16(value)"; } elsif($p{'type'} eq 'int32') { $properties_access_methods .= "g_variant_new_int32(value)"; } elsif($p{'type'} eq 'uint32') { $properties_access_methods .= "g_variant_new_uint32(value)"; } elsif($p{'type'} eq 'int64') { $properties_access_methods .= "g_variant_new_int64(value)"; } elsif($p{'type'} eq 'uint64') { $properties_access_methods .= "g_variant_new_uint64(value)"; } elsif($p{'type'} eq 'double') { $properties_access_methods .= "g_variant_new_double(value)"; } elsif($p{'type'} eq 'object') { $properties_access_methods .= "g_variant_new_object_path(value)"; } elsif($p{'type'} eq 'string') { $properties_access_methods .= "g_variant_new_string(value)"; } elsif($p{'type'} eq 'variant') { $properties_access_methods .= "g_variant_new_variant(value)"; } elsif($p{'type'} eq 'array{string}') { $properties_access_methods .= "g_variant_new_strv(value, -1)"; } elsif($p{'type'} eq 'array{object}') { $properties_access_methods .= "g_variant_new_objv(value, -1)"; } elsif($p{'type'} =~ /^dict/) { $properties_access_methods .= "value"; } else { die "Unknown object type for access property: $p{'type'}\n"; } $properties_access_methods .= ", error);\n". "}\n\n"; } } $properties_access_methods =~ s/\s+$//s; my $output = "$HEADER\n$SOURCE_TEMPLATE"; if (defined $node->{'objectPath'}) { $output =~ s/\{IF_INIT\}\s+(.+?)\s+\{FI_INIT\}/$1/gs; $output =~ s/\s+\{IF_POST_INIT\}.+?\{FI_POST_INIT\}\s+/\n\n/gs; $output =~ s/\s+\{IF_NO_OBJECT_PATH\}.+?\{FI_NO_OBJECT_PATH\}//gs; } else { $output =~ s/\{IF_POST_INIT\}\s+(.+?)\s+\{FI_POST_INIT\}/$1/gs; $output =~ s/\s+\{IF_INIT\}.+?\{FI_INIT\}\s+/\n/gs; $output =~ s/\{IF_NO_OBJECT_PATH\}\s+(.+?)\s+\{FI_NO_OBJECT_PATH\}/$1/gs; } if (scalar keys %{$node->{$intf}{'signals'}} > 0) { $output =~ s/\{IF_SIGNALS\}\s+(.+?)\s+\{FI_SIGNALS\}/$1/gs; } else { $output =~ s/\s+\{IF_SIGNALS\}.+?\{FI_SIGNALS\}//gs; } if (scalar keys %{$node->{$intf}{'properties'}} > 0) { $output =~ s/\{IF_PROPERTIES\}\s+(.+?)\s+\{FI_PROPERTIES\}/$1/gs; } else { $output =~ s/\s+\{IF_PROPERTIES\}.+?\{FI_PROPERTIES\}//gs; } if (scalar keys %{$node->{$intf}{'properties'}} > 0) { $output =~ s/\{IF_PROPERTIES_EXT\}\s+(.+?)\s+\{FI_PROPERTIES_EXT\}/$1/gs; } else { $output =~ s/\s+\{IF_PROPERTIES_EXT\}.+?\{FI_PROPERTIES_EXT\}//gs; } if (scalar keys %{$node->{$intf}{'methods'}} > 0 or not defined $node->{'serviceName'} or not defined $node->{'objectPath'}) { $output =~ s/\{IF_METHODS\}\s+(.+?)\s+\{FI_METHODS\}/$1/gs; } else { $output =~ s/\s+\{IF_METHODS\}.+?\{FI_METHODS\}\n//gs; } $output =~ s/{\$conn}/$node->{'dbus_conn'}/g; $output =~ s/{CONSTRUCTOR_PROPERTIES}/$constructor_properties/; $output =~ s/{CONSTRUCTOR_CALL}/$constructor_call/; $output =~ s/{CONSTRUCTOR_GETTERS}/$constructor_getters/; $output =~ s/{CONSTRUCTOR_SETTERS}/$constructor_setters/; $output =~ s/{CONSTRUCTOR}/$constructor_def/; $output =~ s/{\$dbus_type}/$dbus_type/; $output =~ s/{PROPERTIES_ACCESS_METHODS}/$properties_access_methods/; $output =~ s/{METHODS}/$methods/; $output =~ s/{\$OBJECT}/$obj_uc/g; $output =~ s/{\$Object}/$obj/g; $output =~ s/{\$object}/$obj_lc/g; # Some formatting fixes $output =~ s/\s+?(\t*\})/\n$1/g; $output =~ s/(switch \(\w+\) \{\n)\s+?(\t+default:)/$1$2/s; $output =~ s/\s+$/\n\n/s; return $output; } my $data = parse_doc_api($ARGV[1], $ARGV[2]); print generate_header($data) if $ARGV[0] eq '-header'; print generate_source($data) if $ARGV[0] eq '-source';bluez-tools-2.0~20170911.0.7cb788c/contrib/generate-bluez-gobjects.sh000077500000000000000000000302311315563672100246150ustar00rootroot00000000000000#!/bin/sh # BlueZ API API_VERSION=5.20-fixed # adapter-api.txt echo "adapter-api.txt" echo "Generating adapter header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/adapter-api.txt > out/adapter.h echo "Generating adapter source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/adapter-api.txt > out/adapter.c # agent-api.txt echo "agent-api.txt" echo "Generating agent manager header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/agent-api.txt 1 > out/agent_manager.h echo "Generating agent manager source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/agent-api.txt 1 > out/agent_manager.c # echo "Generating agent header" # ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/agent-api.txt 2 > out/agent.h # echo "Generating agent source" # ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/agent-api.txt 2 > out/agent.c # alert-api.txt echo "alert-api.txt" echo "Generating alert header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/alert-api.txt 1 > out/alert.h echo "Generating alert source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/alert-api.txt 1 > out/alert.c echo "Generating alert agent header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/alert-api.txt 2 > out/alert_agent.h echo "Generating alert agent source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/alert-api.txt 2 > out/alert_agent.c # cyclingspeed-api.txt echo "cyclingspeed-api.txt" echo "Generating cycling speed manager header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/cyclingspeed-api.txt 1 > out/cycling_speed_manager.h echo "Generating cycling speed manager source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/cyclingspeed-api.txt 1 > out/cycling_speed_manager.c echo "Generating cycling speed header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/cyclingspeed-api.txt 2 > out/cycling_speed.h echo "Generating cycling speed source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/cyclingspeed-api.txt 2 > out/cycling_speed.c # echo "Generating cycling watcher header" # ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/cyclingspeed-api.txt 3 > out/cycling_speed_watcher.h # echo "Generating cycling watcher source" # ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/cyclingspeed-api.txt 3 > out/cycling_speed_watcher.c # device-api.txt echo "device-api.txt" echo "Generating device header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/device-api.txt > out/device.h echo "Generating device source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/device-api.txt > out/device.c # health-api.txt echo "health-api.txt" echo "Generating health manager header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/health-api.txt 1 > out/health_manager.h echo "Generating health manager source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/health-api.txt 1 > out/health_manager.c echo "Generating health device header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/health-api.txt 2 > out/health_device.h echo "Generating health device source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/health-api.txt 2 > out/health_device.c echo "Generating health channel header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/health-api.txt 3 > out/health_channel.h echo "Generating health channel source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/health-api.txt 3 > out/health_channel.c # heartrate-api.txt echo "heartrate-api.txt" echo "Generating heart rate manager header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/heartrate-api.txt 1 > out/heart_rate_manager.h echo "Generating heart rate manager source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/heartrate-api.txt 1 > out/heart_rate_manager.c echo "Generating heart rate header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/heartrate-api.txt 2 > out/heart_rate.h echo "Generating heart rate source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/heartrate-api.txt 2 > out/heart_rate.c # echo "Generating heart rate watcher header" # ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/heartrate-api.txt 3 > out/heart_rate_watcher.h # echo "Generating heart rate watcher source" # ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/heartrate-api.txt 3 > out/heart_rate_watcher.c # media-api.txt echo "media-api.txt" echo "Generating media header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/media-api.txt 1 > out/media.h echo "Generating media source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/media-api.txt 1 > out/media.c echo "Generating media control header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/media-api.txt 2 > out/media_control.h echo "Generating media control source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/media-api.txt 2 > out/media_control.c echo "Generating media player header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/media-api.txt 3 > out/media_player.h echo "Generating media player source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/media-api.txt 3 > out/media_player.c # echo "Generating media folder header" # ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/media-api.txt 4 > out/media_folder.h # echo "Generating media folder source" # ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/media-api.txt 4 > out/media_folder.c # echo "Generating media item header" # ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/media-api.txt 5 > out/media_item.h # echo "Generating media item source" # ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/media-api.txt 5 > out/media_item.c # echo "Generating media endpoint header" # ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/media-api.txt 6 > out/media_endpoint.h # echo "Generating media endpoint source" # ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/media-api.txt 6 > out/media_endpoint.c # echo "Generating media transport header" # ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/media-api.txt 7 > out/media_transport.h # echo "Generating media transport source" # ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/media-api.txt 7 > out/media_transport.c # network-api.txt echo "network-api.txt" echo "Generating network header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/network-api.txt 1 > out/network.h echo "Generating network source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/network-api.txt 1 > out/network.c echo "Generating network server header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/network-api.txt 2 > out/network_server.h echo "Generating network server source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/network-api.txt 2 > out/network_server.c # obex-agent-api.txt echo "obex-agent-api.txt" echo "Generating obex agent manager header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/obex-agent-api.txt 1 > out/obex/obex_agent_manager.h echo "Generating obex agent manager source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/obex-agent-api.txt 1 > out/obex/obex_agent_manager.c # echo "Generating obex agent header" # ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/obex-agent-api.txt 2 > out/obex/obex_agent.h # echo "Generating obex agent source" # ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/obex-agent-api.txt 2 > out/obex/obex_agent.c # obex-api.txt echo "obex-api.txt" echo "Generating obex client header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/obex-api.txt 1 > out/obex/obex_client.h echo "Generating obex client source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/obex-api.txt 1 > out/obex/obex_client.c echo "Generating obex session header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/obex-api.txt 2 > out/obex/obex_session.h echo "Generating obex session source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/obex-api.txt 2 > out/obex/obex_session.c echo "Generating obex transfer header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/obex-api.txt 3 > out/obex/obex_transfer.h echo "Generating obex transfer source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/obex-api.txt 3 > out/obex/obex_transfer.c echo "Generating obex object push header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/obex-api.txt 4 > out/obex/obex_object_push.h echo "Generating obex object push source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/obex-api.txt 4 > out/obex/obex_object_push.c echo "Generating obex file transfer header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/obex-api.txt 5 > out/obex/obex_file_transfer.h echo "Generating obex file transfer source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/obex-api.txt 5 > out/obex/obex_file_transfer.c echo "Generating obex phonebook access header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/obex-api.txt 6 > out/obex/obex_phonebook_access.h echo "Generating obex phonebook access source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/obex-api.txt 6 > out/obex/obex_phonebook_access.c echo "Generating obex synchronization header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/obex-api.txt 7 > out/obex/obex_synchronization.h echo "Generating obex synchronization source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/obex-api.txt 7 > out/obex/obex_synchronization.c echo "Generating obex message access header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/obex-api.txt 8 > out/obex/obex_message_access.h echo "Generating obex message access source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/obex-api.txt 8 > out/obex/obex_message_access.c echo "Generating obex message header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/obex-api.txt 9 > out/obex/obex_message.h echo "Generating obex message source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/obex-api.txt 9 > out/obex/obex_message.c # profile-api.txt echo "profile-api.txt" echo "Generating profile manager header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/profile-api.txt 1 > out/profile_manager.h echo "Generating profile manager source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/profile-api.txt 1 > out/profile_manager.c # echo "Generating profile header" # ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/profile-api.txt 2 > out/profile.h # echo "Generating profile source" # ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/profile-api.txt 2 > out/profile.c # proximity-api.txt echo "proximity-api.txt" echo "Generating proximity monitor header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/proximity-api.txt 1 > out/proximity_monitor.h echo "Generating proximity monitor source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/proximity-api.txt 1 > out/proximity_monitor.c echo "Generating proximity reporter header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/proximity-api.txt 2 > out/proximity_reporter.h echo "Generating proximity reporter source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/proximity-api.txt 2 > out/proximity_reporter.c # sap-api.txt echo "sap-api.txt" echo "Generating sim access header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/sap-api.txt > out/sim_access.h echo "Generating sim access source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/sap-api.txt > out/sim_access.c # thermometer-api.txt echo "thermometer-api.txt" echo "Generating thermometer manager header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/thermometer-api.txt 1 > out/thermometer_manager.h echo "Generating thermometer manager source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/thermometer-api.txt 1 > out/thermometer_manager.c echo "Generating thermometer header" ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/thermometer-api.txt 2 > out/thermometer.h echo "Generating thermometer source" ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/thermometer-api.txt 2 > out/thermometer.c # echo "Generating thermometer watcher header" # ./gen-dbus-gobject.pl -header bluez-api-${API_VERSION}/thermometer-api.txt 3 > out/thermometer_watcher.h # echo "Generating thermometer watcher source" # ./gen-dbus-gobject.pl -source bluez-api-${API_VERSION}/thermometer-api.txt 3 > out/thermometer_watcher.c bluez-tools-2.0~20170911.0.7cb788c/contrib/man/000077500000000000000000000000001315563672100203235ustar00rootroot00000000000000bluez-tools-2.0~20170911.0.7cb788c/contrib/man/bt-adapter.pod000066400000000000000000000051201315563672100230500ustar00rootroot00000000000000=head1 NAME bt-adapter - a bluetooth adapter manager =head1 SYNOPSIS bt-adapter [OPTION...] Help Options: -h, --help Application Options: -l, --list -a, --adapter= -i, --info -d, --discover --set =head1 DESCRIPTION This utility is used to manage Bluetooth adapters. You can list all available adapters, show information about adapter, change adapter properties or discover remote devices. =head1 OPTIONS B<-h, --help> Show help B<-l, --list> List all available adapters B<-a, --adapter Ename|macE> Specify adapter to use by his Name or MAC address (if this option does not defined - default adapter used) B<-i, --info> Show information about adapter (returns all properties) B<-d, --discover> Discover remote devices (with remote device name resolving) B<--set EpropertyE EvalueE> Change adapter properties (see ADAPTER PROPERTIES section for list of available properties) =head1 ADAPTER PROPERTIES string Address [ro] The Bluetooth adapter address (MAC). string Alias [rw] The Bluetooth adapter friendly name. uint32 Class [ro] The Bluetooth class of device. boolean Powered [rw] Switch an adapter on or off. This will also set the appropiate connectable state. boolean Discoverable [rw] Switch an adapter to discoverable or non-discoverable to either make it visible or hide it. If the DiscoverableTimeout is set to a non-zero value then the system will set this value back to false after the timer expired. In case the adapter is switched off, setting this value will fail. boolean Pairable [rw] Switch an adapter to pairable or non-pairable. Note that this property only affects incoming pairing requests. uint32 PaireableTimeout [rw] The pairable timeout in seconds. A value of zero means that the timeout is disabled and it will stay in pareable mode forever. uint32 DiscoverableTimeout [rw] The discoverable timeout in seconds. A value of zero means that the timeout is disabled and it will stay in discoverable/limited mode forever. The default value for the discoverable timeout should be 180 seconds (3 minutes). boolean Discovering [ro] Indicates that a device discovery procedure is active. list UUIDs [ro] List of 128-bit UUIDs that represents the available local services. =head1 AUTHOR Alexander Orlenko . =head1 SEE ALSO bt-agent(1) bt-device(1) bt-network(1) bluez-tools-2.0~20170911.0.7cb788c/contrib/man/bt-agent.pod000066400000000000000000000031171315563672100225320ustar00rootroot00000000000000=head1 NAME bt-adapter - a bluetooth agent =head1 SYNOPSIS bt-agent [OPTION...] Help Options: -h, --help Application Options: -c, --capability= -p, --pin -d, --daemon =head1 DESCRIPTION This interactive utility is used to manage incoming Bluetooth requests (eg. request of pincode, request of authorize a connection/service request, etc). =head1 OPTIONS B<-h, --help> Show help B<-c, --capability EcapabilityE> Specify the input and output capabilities of the agent. `capability` can be one of: DisplayOnly DisplayYesNo (default) KeyboardOnly NoInputNoOutput (if this option does not defined - `DisplayYesNo' will be used) B<-p, --pin Efile path> Use a file that holds a list of authorization codes for each device by name or mac address. The contents of the file should be in this format: AA:BB:CC:DD:EE:FF 123456 RemoteDeviceName * (accept any pin code) If a pin file is included, it will check the passkey of the pairing device against the key included in the file. It will automatically authorize the device if the key matches, otherwise it will request the user for manual authorization. B<-d, --daemon> Run the agent as a background process (as a daemon). The agent will rely on a pin file and request no manual user authorization. Any devices that attempt to pair without a valid passkey defined in the pin file will be automatically rejected. =head1 AUTHOR Alexander Orlenko . =head1 SEE ALSO bt-adapter(1) bt-device(1) bt-network(1) bluez-tools-2.0~20170911.0.7cb788c/contrib/man/bt-audio.pod000066400000000000000000000015341315563672100225360ustar00rootroot00000000000000=head1 NAME bt-audio - a bluetooth generic audio manager =head1 SYNOPSIS bt-audio [OPTION...] Help Options: -h, --help Application Options: -a, --adapter= -c, --connect= -d, --disconnect= =head1 DESCRIPTION This utility is used to manage outgoing audio service connections. =head1 OPTIONS B<-h, --help> Show help B<-a, --adapter Ename|macE> Specify adapter to use by his Name or MAC address (if this option does not defined - default adapter used) B<-c, --connect Ename|macE> Connect all supported audio profiles on the device B<-d, --disconnect Ename|macE> Disconnect all audio profiles on the device =head1 AUTHOR Alexander Orlenko . =head1 SEE ALSO bt-adapter(1) bt-agent(1) bt-device(1) bt-input(1) bt-monitor(1) bt-network(1) bt-serial(1) bluez-tools-2.0~20170911.0.7cb788c/contrib/man/bt-device.pod000066400000000000000000000060301315563672100226700ustar00rootroot00000000000000=head1 NAME bt-device - a bluetooth device manager =head1 SYNOPSIS bt-device [OPTION...] Help Options: -h, --help Application Options: -a, --adapter= -l, --list -c, --connect= -d, --disconnect= -r, --remove= -i, --info= -s, --services [] --set -v, --verbose =head1 DESCRIPTION This utility is used to manage Bluetooth devices. You can list added devices, connect to a new device, disconnect device, remove added device, show info about device, discover remote device services or change device properties. =head1 OPTIONS B<-h, --help> Show help B<-a, --adapter Ename|macE> Specify adapter to use by his Name or MAC address (if this option does not defined - default adapter used) B<-l, --list> List added devices B<-c, --connect EmacE> Connect to the remote device by his MAC, retrieve all SDP records and then initiate the pairing B<-d, --disconnect Ename|macE> Disconnects a specific remote device by terminating the low-level ACL connection. B<-r, --remove> Remove device (and also the pairing information) B<-i, --info> Show information about device (returns all properties) B<-s, --services Ename|macE [EpatternE]> Starts the service discovery to retrieve remote service records, the `pattern` parameter can be used to specify specific UUIDs B<--set EpropertyE EvalueE> Change device properties (see DEVICE PROPERTIES section for list of available properties) B<-v, --verbose> Verbosely display remote service records (affect to service discovery mode) =head1 DEVICE PROPERTIES string Address [ro] The Bluetooth device address (MAC) of the remote device. string Name [ro] The Bluetooth remote device name. string Icon [ro] Proposed icon name according to the freedesktop.org icon naming specification. uint32 Class [ro] The Bluetooth class of device of the remote device. list UUIDs [ro] List of 128-bit UUIDs that represents the available remote services. boolean Paired [ro] Indicates if the remote device is paired. boolean Connected [ro] Indicates if the remote device is currently connected. boolean Trusted [rw] Indicates if the remote is seen as trusted. boolean Blocked [rw] If set to true any incoming connections from the device will be immediately rejected. string Alias [rw] The name alias for the remote device. The alias can be used to have a different friendly name for the remote device. In case no alias is set, it will return the remote device name. Setting an empty string as alias will convert it back to the remote device name. boolean LegacyPairing [ro] Set to true if the device only supports the pre-2.1 pairing mechanism. =head1 AUTHOR Alexander Orlenko . =head1 SEE ALSO bt-adapter(1) bt-agent(1) bt-network(1) bluez-tools-2.0~20170911.0.7cb788c/contrib/man/bt-input.pod000066400000000000000000000014701315563672100225730ustar00rootroot00000000000000=head1 NAME bt-input - a bluetooth input manager =head1 SYNOPSIS bt-input [OPTION...] Help Options: -h, --help Application Options: -a, --adapter= -c, --connect= -d, --disconnect= =head1 DESCRIPTION This utility is used to manage outgoing input (HID) service connections. =head1 OPTIONS B<-h, --help> Show help B<-a, --adapter Ename|macE> Specify adapter to use by his Name or MAC address (if this option does not defined - default adapter used) B<-c, --connect Ename|macE> Connect to the input device B<-d, --disconnect Ename|macE> Disconnect from the input device =head1 AUTHOR Alexander Orlenko . =head1 SEE ALSO bt-adapter(1) bt-agent(1) bt-audio(1) bt-device(1) bt-monitor(1) bt-network(1) bt-serial(1) bluez-tools-2.0~20170911.0.7cb788c/contrib/man/bt-monitor.pod000066400000000000000000000017271315563672100231300ustar00rootroot00000000000000=head1 NAME bt-monitor - a bluetooth monitor =head1 SYNOPSIS bt-monitor [OPTION...] Help Options: -h, --help Application Options: -a, --adapter= =head1 DESCRIPTION This utility is used to capture DBus signals of bluetoothd. Captured next signals: B: AdapterAdded AdapterRemoved DefaultAdapterChanged B: DeviceCreated DeviceDisappeared DeviceFound DeviceRemoved AdapterPropertyChanged B: DisconnectRequested DevicePropertyChanged B: AudioServiceConnected InputServiceConnected NetworkServiceConnected =head1 OPTIONS B<-h, --help> Show help B<-a, --adapter Ename|macE> Specify adapter to capture by his Name or MAC address (if this option does not defined - all adapters captured) =head1 AUTHOR Alexander Orlenko . =head1 SEE ALSO bt-adapter(1) bt-agent(1) bt-audio(1) bt-device(1) bt-input(1) bt-network(1) bt-serial(1) bluez-tools-2.0~20170911.0.7cb788c/contrib/man/bt-network.pod000066400000000000000000000020531315563672100231230ustar00rootroot00000000000000=head1 NAME bt-network - a bluetooth network manager =head1 SYNOPSIS bt-network [OPTION...] Help Options: -h, --help Application Options: -a, --adapter= -c, --connect -s, --server =head1 DESCRIPTION This utility is used to manage network services (client/server). All servers will be automatically unregistered when the application terminates. =head1 OPTIONS B<-h, --help> Show help B<-a, --adapter Ename|macE> Specify adapter to use by his Name or MAC address (if this option does not defined - default adapter used) B<-c, --connect Ename|macE EuuidE> Connect to the network device and return the network interface name, uuid can be either one of "gn", "panu" or "nap" B<-s, --server Egn|panu|napE EbrigeE> Register server for the provided UUID, every new connection to this server will be added the bridge interface =head1 AUTHOR Alexander Orlenko . =head1 SEE ALSO bt-adapter(1) bt-agent(1) bt-device(1) bluez-tools-2.0~20170911.0.7cb788c/contrib/man/bt-obex.pod000066400000000000000000000037661315563672100224030ustar00rootroot00000000000000=head1 NAME bt-obex - a bluetooth OBEX client/server =head1 SYNOPSIS bt-obex [OPTION...] Help Options: -h, --help Application Options: -a, --adapter= -s, --server [] -p, --opp -f, --ftp= =head1 DESCRIPTION This utility implemented support of Object Push Profile (OPP) and File Transfer Profile (FTP). You can send and receive files to/from remote device using this tool. =head1 OPTIONS B<-h, --help> Show help B<-a, --adapter Ename|macE> Specify adapter to use by his Name or MAC address (if this option does not defined - default adapter used) B<-s, --server [EpathE]> Register agent at OBEX server and set incoming/root directory to `path` or current folder will be used; Agent is used to accept/reject incoming bluetooth object push requests B<-p, --opp Ename|macE EfileE> Send local file to the specified remote device using object push profile B<-f, --ftp Ename|macE> Start FTP session with remote device; If session opened successfuly, FTP shell will be opened FTP commands: help Show help message exit Close FTP session cd Change the current folder of the remote device mkdir Create a new folder in the remote device ls List folder contents get Copy the src file (from remote device) to the dst file (on local filesystem) put Copy the src file (from local filesystem) to the dst file (on remote device) cp Copy a file within the remote device from src file to dst file mv Move a file within the remote device from src file to dst file rm Deletes the specified file/folder =head1 AUTHOR Alexander Orlenko . =head1 SEE ALSO bt-adapter(1) bt-agent(1) bt-device(1) bt-network(1) bluez-tools-2.0~20170911.0.7cb788c/contrib/man/bt-serial.pod000066400000000000000000000020361315563672100227120ustar00rootroot00000000000000=head1 NAME bt-serial - a bluetooth serial manager =head1 SYNOPSIS bt-serial [OPTION...] Help Options: -h, --help Application Options: -a, --adapter= -c, --connect -d, --disconnect =head1 DESCRIPTION This utility is used to manage serial service connections. =head1 OPTIONS B<-h, --help> Show help B<-a, --adapter Ename|macE> Specify adapter to use by his Name or MAC address (if this option does not defined - default adapter used) B<-c, --connect Ename|macE EpatternE> Connects to a specific RFCOMM based service on a remote device and then creates a RFCOMM TTY device for it; `pattern` is a profile short name (spp, dun), RFCOMM channel (1-30) B<-d, --disconnect Ename|macE Etty_deviceE> Disconnect a RFCOMM TTY device that has been created =head1 AUTHOR Alexander Orlenko . =head1 SEE ALSO bt-adapter(1) bt-agent(1) bt-audio(1) bt-device(1) bt-input(1) bt-monitor(1) bt-network(1) bluez-tools-2.0~20170911.0.7cb788c/git-version-gen000077500000000000000000000131051315563672100210530ustar00rootroot00000000000000#!/bin/sh # Print a version string. scriptversion=2010-06-14.19; # UTC # Copyright (C) 2007-2010 Free Software Foundation, Inc. # # This program is free software: you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 3 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program. If not, see . # This script is derived from GIT-VERSION-GEN from GIT: http://git.or.cz/. # It may be run two ways: # - from a git repository in which the "git describe" command below # produces useful output (thus requiring at least one signed tag) # - from a non-git-repo directory containing a .tarball-version file, which # presumes this script is invoked like "./git-version-gen .tarball-version". # In order to use intra-version strings in your project, you will need two # separate generated version string files: # # .tarball-version - present only in a distribution tarball, and not in # a checked-out repository. Created with contents that were learned at # the last time autoconf was run, and used by git-version-gen. Must not # be present in either $(srcdir) or $(builddir) for git-version-gen to # give accurate answers during normal development with a checked out tree, # but must be present in a tarball when there is no version control system. # Therefore, it cannot be used in any dependencies. GNUmakefile has # hooks to force a reconfigure at distribution time to get the value # correct, without penalizing normal development with extra reconfigures. # # .version - present in a checked-out repository and in a distribution # tarball. Usable in dependencies, particularly for files that don't # want to depend on config.h but do want to track version changes. # Delete this file prior to any autoconf run where you want to rebuild # files to pick up a version string change; and leave it stale to # minimize rebuild time after unrelated changes to configure sources. # # It is probably wise to add these two files to .gitignore, so that you # don't accidentally commit either generated file. # # Use the following line in your configure.ac, so that $(VERSION) will # automatically be up-to-date each time configure is run (and note that # since configure.ac no longer includes a version string, Makefile rules # should not depend on configure.ac for version updates). # # AC_INIT([GNU project], # m4_esyscmd([build-aux/git-version-gen .tarball-version]), # [bug-project@example]) # # Then use the following lines in your Makefile.am, so that .version # will be present for dependencies, and so that .tarball-version will # exist in distribution tarballs. # # BUILT_SOURCES = $(top_srcdir)/.version # $(top_srcdir)/.version: # echo $(VERSION) > $@-t && mv $@-t $@ # dist-hook: # echo $(VERSION) > $(distdir)/.tarball-version case $# in 1|2) ;; *) echo 1>&2 "Usage: $0 \$srcdir/.tarball-version" \ '[TAG-NORMALIZATION-SED-SCRIPT]' exit 1;; esac tarball_version_file=$1 tag_sed_script="${2:-s/x/x/}" nl=' ' # Avoid meddling by environment variable of the same name. v= # First see if there is a tarball-only version file. # then try "git describe", then default. if test -f $tarball_version_file then v=`cat $tarball_version_file` || exit 1 case $v in *$nl*) v= ;; # reject multi-line output [0-9]*) ;; *) v= ;; esac test -z "$v" \ && echo "$0: WARNING: $tarball_version_file seems to be damaged" 1>&2 fi if test -n "$v" then : # use $v elif test -d .git \ && v=`git describe --abbrev=4 --match='v*' HEAD 2>/dev/null \ || git describe --abbrev=4 HEAD 2>/dev/null` \ && v=`printf '%s\n' "$v" | sed "$tag_sed_script"` \ && case $v in v[0-9]*) ;; *) (exit 1) ;; esac then # Is this a new git that lists number of commits since the last # tag or the previous older version that did not? # Newer: v6.10-77-g0f8faeb # Older: v6.10-g0f8faeb case $v in *-*-*) : git describe is okay three part flavor ;; *-*) : git describe is older two part flavor # Recreate the number of commits and rewrite such that the # result is the same as if we were using the newer version # of git describe. vtag=`echo "$v" | sed 's/-.*//'` numcommits=`git rev-list "$vtag"..HEAD | wc -l` v=`echo "$v" | sed "s/\(.*\)-\(.*\)/\1-$numcommits-\2/"`; ;; esac # Change the first '-' to a '.', so version-comparing tools work properly. # Remove the "g" in git describe's output string, to save a byte. v=`echo "$v" | sed 's/-/./;s/\(.*\)-g/\1-/'`; else v=UNKNOWN fi v=`echo "$v" |sed 's/^v//'` # Don't declare a version "dirty" merely because a time stamp has changed. git update-index --refresh > /dev/null 2>&1 dirty=`sh -c 'git diff-index --name-only HEAD' 2>/dev/null` || dirty= case "$dirty" in '') ;; *) # Append the suffix only if there isn't one already. case $v in *-dirty) ;; *) v="$v-dirty" ;; esac ;; esac # Omit the trailing newline, so that m4_esyscmd can use the result directly. echo "$v" | tr -d "$nl" # Local variables: # eval: (add-hook 'write-file-hooks 'time-stamp) # time-stamp-start: "scriptversion=" # time-stamp-format: "%:y-%02m-%02d.%02H" # time-stamp-time-zone: "UTC" # time-stamp-end: "; # UTC" # End: bluez-tools-2.0~20170911.0.7cb788c/src/000077500000000000000000000000001315563672100166775ustar00rootroot00000000000000bluez-tools-2.0~20170911.0.7cb788c/src/Makefile.am000066400000000000000000000054401315563672100207360ustar00rootroot00000000000000AM_CPPFLAGS = $(GLIB_CFLAGS) $(GIO_CFLAGS) LDADD = $(GLIB_LIBS) $(GIO_LIBS) bluez_sources = lib/bluez/adapter.c lib/bluez/adapter.h \ lib/bluez/agent_manager.c lib/bluez/agent_manager.h \ lib/bluez/alert_agent.c lib/bluez/alert_agent.h \ lib/bluez/alert.c lib/bluez/alert.h \ lib/bluez/cycling_speed.c lib/bluez/cycling_speed.h \ lib/bluez/cycling_speed_manager.c lib/bluez/cycling_speed_manager.h \ lib/bluez/device.c lib/bluez/device.h \ lib/bluez/health_channel.c lib/bluez/health_channel.h \ lib/bluez/health_device.c lib/bluez/health_device.h \ lib/bluez/health_manager.c lib/bluez/health_manager.h \ lib/bluez/heart_rate.c lib/bluez/heart_rate.h \ lib/bluez/heart_rate_manager.c lib/bluez/heart_rate_manager.h \ lib/bluez/media.c lib/bluez/media.h \ lib/bluez/media_control.c lib/bluez/media_control.h \ lib/bluez/media_player.c lib/bluez/media_player.h \ lib/bluez/network.c lib/bluez/network.h \ lib/bluez/network_server.c lib/bluez/network_server.h \ lib/bluez/obex/obex_agent_manager.c lib/bluez/obex/obex_agent_manager.h \ lib/bluez/obex/obex_client.c lib/bluez/obex/obex_client.h \ lib/bluez/obex/obex_file_transfer.c lib/bluez/obex/obex_file_transfer.h \ lib/bluez/obex/obex_message_access.c lib/bluez/obex/obex_message_access.h \ lib/bluez/obex/obex_message.c lib/bluez/obex/obex_message.h \ lib/bluez/obex/obex_object_push.c lib/bluez/obex/obex_object_push.h \ lib/bluez/obex/obex_phonebook_access.c lib/bluez/obex/obex_phonebook_access.h \ lib/bluez/obex/obex_session.c lib/bluez/obex/obex_session.h \ lib/bluez/obex/obex_synchronization.c lib/bluez/obex/obex_synchronization.h \ lib/bluez/obex/obex_transfer.c lib/bluez/obex/obex_transfer.h \ lib/bluez/profile_manager.c lib/bluez/profile_manager.h \ lib/bluez/proximity_monitor.c lib/bluez/proximity_monitor.h \ lib/bluez/proximity_reporter.c lib/bluez/proximity_reporter.h \ lib/bluez/sim_access.c lib/bluez/sim_access.h \ lib/bluez/thermometer.c lib/bluez/thermometer.h \ lib/bluez/thermometer_manager.c lib/bluez/thermometer_manager.h lib_sources = lib/agent-helper.c lib/agent-helper.h \ lib/dbus-common.c lib/dbus-common.h \ lib/helpers.c lib/helpers.h \ lib/manager.c lib/manager.h \ lib/obex_agent.c lib/obex_agent.h \ lib/properties.c lib/properties.h \ lib/sdp.c lib/sdp.h \ lib/bluez-api.h bin_PROGRAMS = bt-adapter bt-agent bt-device bt-network bt-obex bt_adapter_SOURCES = $(lib_sources) $(bluez_sources) bt-adapter.c bt_agent_SOURCES = $(lib_sources) $(bluez_sources) bt-agent.c bt_device_SOURCES = $(lib_sources) $(bluez_sources) bt-device.c bt_network_SOURCES = $(lib_sources) $(bluez_sources) bt-network.c bt_obex_SOURCES = $(lib_sources) $(bluez_sources) bt-obex.c bt_obex_LDADD = $(LDADD) $(LIBREADLINE) dist_man_MANS = bt-adapter.1 bt-agent.1 bt-device.1 bt-network.1 bt-obex.1 bluez-tools-2.0~20170911.0.7cb788c/src/bt-adapter.1000066400000000000000000000154361315563672100210150ustar00rootroot00000000000000.\" Automatically generated by Pod::Man 2.27 (Pod::Simple 3.28) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is turned on, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{ . if \nF \{ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" .\" Accent mark definitions (@(#)ms.acc 1.5 88/02/08 SMI; from UCB 4.2). .\" Fear. Run. Save yourself. No user-serviceable parts. . \" fudge factors for nroff and troff .if n \{\ . ds #H 0 . ds #V .8m . ds #F .3m . ds #[ \f1 . ds #] \fP .\} .if t \{\ . ds #H ((1u-(\\\\n(.fu%2u))*.13m) . ds #V .6m . ds #F 0 . ds #[ \& . ds #] \& .\} . \" simple accents for nroff and troff .if n \{\ . ds ' \& . ds ` \& . ds ^ \& . ds , \& . ds ~ ~ . ds / .\} .if t \{\ . ds ' \\k:\h'-(\\n(.wu*8/10-\*(#H)'\'\h"|\\n:u" . ds ` \\k:\h'-(\\n(.wu*8/10-\*(#H)'\`\h'|\\n:u' . ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'^\h'|\\n:u' . ds , \\k:\h'-(\\n(.wu*8/10)',\h'|\\n:u' . ds ~ \\k:\h'-(\\n(.wu-\*(#H-.1m)'~\h'|\\n:u' . ds / \\k:\h'-(\\n(.wu*8/10-\*(#H)'\z\(sl\h'|\\n:u' .\} . \" troff and (daisy-wheel) nroff accents .ds : \\k:\h'-(\\n(.wu*8/10-\*(#H+.1m+\*(#F)'\v'-\*(#V'\z.\h'.2m+\*(#F'.\h'|\\n:u'\v'\*(#V' .ds 8 \h'\*(#H'\(*b\h'-\*(#H' .ds o \\k:\h'-(\\n(.wu+\w'\(de'u-\*(#H)/2u'\v'-.3n'\*(#[\z\(de\v'.3n'\h'|\\n:u'\*(#] .ds d- \h'\*(#H'\(pd\h'-\w'~'u'\v'-.25m'\f2\(hy\fP\v'.25m'\h'-\*(#H' .ds D- D\\k:\h'-\w'D'u'\v'-.11m'\z\(hy\v'.11m'\h'|\\n:u' .ds th \*(#[\v'.3m'\s+1I\s-1\v'-.3m'\h'-(\w'I'u*2/3)'\s-1o\s+1\*(#] .ds Th \*(#[\s+2I\s-2\h'-\w'I'u*3/5'\v'-.3m'o\v'.3m'\*(#] .ds ae a\h'-(\w'a'u*4/10)'e .ds Ae A\h'-(\w'A'u*4/10)'E . \" corrections for vroff .if v .ds ~ \\k:\h'-(\\n(.wu*9/10-\*(#H)'\s-2\u~\d\s+2\h'|\\n:u' .if v .ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'\v'-.4m'^\v'.4m'\h'|\\n:u' . \" for low resolution devices (crt and lpr) .if \n(.H>23 .if \n(.V>19 \ \{\ . ds : e . ds 8 ss . ds o a . ds d- d\h'-1'\(ga . ds D- D\h'-1'\(hy . ds th \o'bp' . ds Th \o'LP' . ds ae ae . ds Ae AE .\} .rm #[ #] #H #V #F C .\" ======================================================================== .\" .IX Title "bt-adapter 1" .TH bt-adapter 1 "2014-08-01" "" "bluez-tools" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" bt\-adapter \- a bluetooth adapter manager .SH "SYNOPSIS" .IX Header "SYNOPSIS" bt-adapter [\s-1OPTION...\s0] .PP Help Options: \-h, \-\-help .PP Application Options: \-l, \-\-list \-a, \-\-adapter= \-i, \-\-info \-d, \-\-discover \-\-set .SH "DESCRIPTION" .IX Header "DESCRIPTION" This utility is used to manage Bluetooth adapters. You can list all available adapters, show information about adapter, change adapter properties or discover remote devices. .SH "OPTIONS" .IX Header "OPTIONS" \&\fB\-h, \-\-help\fR Show help .PP \&\fB\-l, \-\-list\fR List all available adapters .PP \&\fB\-a, \-\-adapter \fR Specify adapter to use by his Name or \s-1MAC\s0 address (if this option does not defined \- default adapter used) .PP \&\fB\-i, \-\-info\fR Show information about adapter (returns all properties) .PP \&\fB\-d, \-\-discover\fR Discover remote devices (with remote device name resolving) .PP \&\fB\-\-set \fR Change adapter properties (see \s-1ADAPTER PROPERTIES\s0 section for list of available properties) .SH "ADAPTER PROPERTIES" .IX Header "ADAPTER PROPERTIES" string Address [ro] The Bluetooth adapter address (\s-1MAC\s0). .PP string Alias [rw] The Bluetooth adapter friendly name. .PP uint32 Class [ro] The Bluetooth class of device. .PP boolean Powered [rw] Switch an adapter on or off. This will also set the appropiate connectable state. .PP boolean Discoverable [rw] Switch an adapter to discoverable or non-discoverable to either make it visible or hide it. .PP .Vb 3 \& If the DiscoverableTimeout is set to a non\-zero \& value then the system will set this value back to \& false after the timer expired. \& \& In case the adapter is switched off, setting this \& value will fail. .Ve .PP boolean Pairable [rw] Switch an adapter to pairable or non-pairable. .PP .Vb 2 \& Note that this property only affects incoming pairing \& requests. .Ve .PP uint32 PaireableTimeout [rw] The pairable timeout in seconds. A value of zero means that the timeout is disabled and it will stay in pareable mode forever. .PP uint32 DiscoverableTimeout [rw] The discoverable timeout in seconds. A value of zero means that the timeout is disabled and it will stay in discoverable/limited mode forever. .PP .Vb 2 \& The default value for the discoverable timeout should \& be 180 seconds (3 minutes). .Ve .PP boolean Discovering [ro] Indicates that a device discovery procedure is active. .PP list UUIDs [ro] List of 128\-bit UUIDs that represents the available local services. .SH "AUTHOR" .IX Header "AUTHOR" Alexander Orlenko . .SH "SEE ALSO" .IX Header "SEE ALSO" \&\fIbt\-agent\fR\|(1) \fIbt\-device\fR\|(1) \fIbt\-network\fR\|(1) bluez-tools-2.0~20170911.0.7cb788c/src/bt-adapter.c000066400000000000000000000336651315563672100211030ustar00rootroot00000000000000/* * File: main.c * Author: workout * * Created on April 18, 2014, 1:14 PM */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include #include "lib/dbus-common.h" #include "lib/bluez-api.h" #include "lib/helpers.h" static void _adapter_property_changed(GDBusConnection *connection, const gchar *sender_name, const gchar *object_path, const gchar *interface_name, const gchar *signal_name, GVariant *parameters, gpointer user_data) { g_assert(user_data != NULL); GMainLoop *mainloop = user_data; GVariant *changed_properties = g_variant_get_child_value(parameters, 1); GVariant *discovering_variant = g_variant_lookup_value(changed_properties, "Discovering", NULL); if(discovering_variant) { const gboolean discovering = g_variant_get_boolean(discovering_variant); if(!discovering) { g_main_loop_quit(mainloop); } g_variant_unref(discovering_variant); } g_variant_unref(changed_properties); } static void _manager_device_found(GDBusConnection *connection, const gchar *sender_name, const gchar *object_path, const gchar *interface_name, const gchar *signal_name, GVariant *parameters, gpointer user_data) { g_assert(user_data != NULL); const gchar *adapter_object_path = user_data; GVariant *arg0 = g_variant_get_child_value(parameters, 0); const gchar *str_object_path = g_variant_get_string(arg0, NULL); g_variant_unref(arg0); if (!g_str_has_prefix(str_object_path, adapter_object_path)) return; GVariant *interfaces_and_properties = g_variant_get_child_value(parameters, 1); GVariant *properties = NULL; if (g_variant_lookup(interfaces_and_properties, DEVICE_DBUS_INTERFACE, "@a{sv}", &properties)) { g_print("[%s]\n", g_variant_get_string(g_variant_lookup_value(properties, "Address", NULL), NULL)); g_print(" Name: %s\n", g_variant_lookup_value(properties, "Name", NULL) != NULL ? g_variant_get_string(g_variant_lookup_value(properties, "Name", NULL), NULL) : NULL); g_print(" Alias: %s\n", g_variant_lookup_value(properties, "Alias", NULL) != NULL ? g_variant_get_string(g_variant_lookup_value(properties, "Alias", NULL), NULL) : NULL); g_print(" Address: %s\n", g_variant_lookup_value(properties, "Address", NULL) != NULL ? g_variant_get_string(g_variant_lookup_value(properties, "Address", NULL), NULL) : NULL); g_print(" Icon: %s\n", g_variant_lookup_value(properties, "Icon", NULL) != NULL ? g_variant_get_string(g_variant_lookup_value(properties, "Icon", NULL), NULL) : NULL); g_print(" Class: 0x%x\n", g_variant_lookup_value(properties, "Class", NULL) != NULL ? g_variant_get_uint32(g_variant_lookup_value(properties, "Class", NULL)) : 0x0); g_print(" LegacyPairing: %d\n", g_variant_lookup_value(properties, "LegacyPairing", NULL) != NULL ? g_variant_get_boolean(g_variant_lookup_value(properties, "LegacyPairing", NULL)) : FALSE); g_print(" Paired: %d\n", g_variant_lookup_value(properties, "Paired", NULL) != NULL ? g_variant_get_boolean(g_variant_lookup_value(properties, "Paired", NULL)) : FALSE); g_print(" RSSI: %d\n", g_variant_lookup_value(properties, "RSSI", NULL) != NULL ? g_variant_get_int16(g_variant_lookup_value(properties, "RSSI", NULL)) : 0x0); g_print("\n"); g_variant_unref(properties); } g_variant_unref(interfaces_and_properties); } static gboolean list_arg = FALSE; static gchar *adapter_arg = NULL; static gboolean info_arg = FALSE; static gboolean discover_arg = FALSE; static gboolean set_arg = FALSE; static gchar *set_property_arg = NULL; static gchar *set_value_arg = NULL; static GOptionEntry entries[] = { {"list", 'l', 0, G_OPTION_ARG_NONE, &list_arg, "List all available adapters", NULL}, {"adapter", 'a', 0, G_OPTION_ARG_STRING, &adapter_arg, "Adapter Name or MAC", ""}, {"info", 'i', 0, G_OPTION_ARG_NONE, &info_arg, "Show adapter info", NULL}, {"discover", 'd', 0, G_OPTION_ARG_NONE, &discover_arg, "Discover remote devices", NULL}, {"set", 's', 0, G_OPTION_ARG_NONE, &set_arg, "Set adapter property", NULL}, {NULL} }; /* * */ int main(int argc, char *argv[]) { GError *error = NULL; GOptionContext *context; /* Query current locale */ setlocale(LC_CTYPE, ""); // g_type_init(); // DEPRECATED dbus_init(); context = g_option_context_new("- a bluetooth adapter manager"); g_option_context_add_main_entries(context, entries, NULL); g_option_context_set_summary(context, "Version "PACKAGE_VERSION); g_option_context_set_description(context, "Set Options:\n" " --set \n" " Where `property` is one of:\n" " Alias\n" " Discoverable\n" " DiscoverableTimeout\n" " Pairable\n" " PairableTimeout\n" " Powered\n\n" "Report bugs to <"PACKAGE_BUGREPORT">." "Project home page <"PACKAGE_URL">." ); if (!g_option_context_parse(context, &argc, &argv, &error)) { g_print("%s: %s\n", g_get_prgname(), error->message); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } else if (!list_arg && !info_arg && !discover_arg && !set_arg) { g_print("%s", g_option_context_get_help(context, FALSE, NULL)); exit(EXIT_FAILURE); } else if (set_arg && (argc != 3 || strlen(argv[1]) == 0 || strlen(argv[2]) == 0)) { g_print("%s: Invalid arguments for --set\n", g_get_prgname()); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } g_option_context_free(context); if (!dbus_system_connect(&error)) { g_printerr("Couldn't connect to DBus system bus: %s\n", error->message); exit(EXIT_FAILURE); } /* Check, that bluetooth daemon is running */ if (!intf_supported(BLUEZ_DBUS_SERVICE_NAME, MANAGER_DBUS_PATH, MANAGER_DBUS_INTERFACE)) { g_printerr("%s: bluez service is not found\n", g_get_prgname()); g_printerr("Did you forget to run bluetoothd?\n"); exit(EXIT_FAILURE); } Manager *manager = g_object_new(MANAGER_TYPE, NULL); if (list_arg) { const GPtrArray *adapters_list = manager_get_adapters(manager); g_assert(adapters_list != NULL); if (adapters_list->len == 0) { g_print("No adapters found\n"); exit(EXIT_FAILURE); } g_print("Available adapters:\n"); for (int i = 0; i < adapters_list->len; i++) { const gchar *adapter_path = g_ptr_array_index(adapters_list, i); Adapter *adapter = adapter_new(adapter_path); g_print("%s (%s)\n", adapter_get_name(adapter, &error), adapter_get_address(adapter, &error)); g_object_unref(adapter); } } else if (info_arg) { Adapter *adapter = find_adapter(adapter_arg, &error); exit_if_error(error); gchar *adapter_intf = g_path_get_basename(adapter_get_dbus_object_path(adapter)); g_print("[%s]\n", adapter_intf); g_print(" Name: %s\n", adapter_get_name(adapter, &error)); g_print(" Address: %s\n", adapter_get_address(adapter, &error)); g_print(" Alias: %s [rw]\n", adapter_get_alias(adapter, &error)); g_print(" Class: 0x%x\n", adapter_get_class(adapter, &error)); g_print(" Discoverable: %d [rw]\n", adapter_get_discoverable(adapter, &error)); g_print(" DiscoverableTimeout: %d [rw]\n", adapter_get_discoverable_timeout(adapter, &error)); g_print(" Discovering: %d\n", adapter_get_discovering(adapter, &error)); g_print(" Pairable: %d [rw]\n", adapter_get_pairable(adapter, &error)); g_print(" PairableTimeout: %d [rw]\n", adapter_get_pairable_timeout(adapter, &error)); g_print(" Powered: %d [rw]\n", adapter_get_powered(adapter, &error)); g_print(" UUIDs: ["); const gchar **uuids = adapter_get_uuids(adapter, &error); for (int j = 0; uuids[j] != NULL; j++) { if (j > 0) g_print(", "); g_print("%s", uuid2name(uuids[j])); } g_print("]\n"); g_free(adapter_intf); g_object_unref(adapter); } else if (discover_arg) { Adapter *adapter = find_adapter(adapter_arg, &error); exit_if_error(error); // To store pairs MAC => Name GHashTable *found_devices = g_hash_table_new(g_str_hash, g_str_equal); // Mainloop GMainLoop *mainloop = g_main_loop_new(NULL, FALSE); guint object_sig_sub_id = g_dbus_connection_signal_subscribe(system_conn, "org.bluez", "org.freedesktop.DBus.ObjectManager", "InterfacesAdded", NULL, NULL, G_DBUS_SIGNAL_FLAGS_NONE, _manager_device_found, (gpointer) adapter_get_dbus_object_path(adapter), NULL); exit_if_error(error); guint prop_sig_sub_id = g_dbus_connection_signal_subscribe(system_conn, "org.bluez", "org.freedesktop.DBus.Properties", "PropertiesChanged", adapter_get_dbus_object_path(adapter), NULL, G_DBUS_SIGNAL_FLAGS_NONE, _adapter_property_changed, mainloop, NULL); exit_if_error(error); g_print("Searching...\n"); adapter_start_discovery(adapter, &error); exit_if_error(error); g_main_loop_run(mainloop); /* Discovering process here... */ g_main_loop_unref(mainloop); g_dbus_connection_signal_unsubscribe(system_conn, object_sig_sub_id); exit_if_error(error); g_dbus_connection_signal_unsubscribe(system_conn, prop_sig_sub_id); exit_if_error(error); g_print("Done\n"); g_hash_table_unref(found_devices); g_object_unref(adapter); } else if (set_arg) { set_property_arg = argv[1]; set_value_arg = argv[2]; Adapter *adapter = find_adapter(adapter_arg, &error); exit_if_error(error); GVariant *v = NULL; if (g_strcmp0(set_property_arg, "Alias") == 0) { v = g_variant_new_string(set_value_arg); } else if ( g_strcmp0(set_property_arg, "Discoverable") == 0 || g_strcmp0(set_property_arg, "Pairable") == 0 || g_strcmp0(set_property_arg, "Powered") == 0 ) { if (g_strcmp0(set_value_arg, "0") == 0 || g_ascii_strcasecmp(set_value_arg, "FALSE") == 0 || g_ascii_strcasecmp(set_value_arg, "OFF") == 0) { v = g_variant_new_boolean(FALSE); } else if (g_strcmp0(set_value_arg, "1") == 0 || g_ascii_strcasecmp(set_value_arg, "TRUE") == 0 || g_ascii_strcasecmp(set_value_arg, "ON") == 0) { v = g_variant_new_boolean(TRUE); } else { g_print("%s: Invalid boolean value: %s\n", g_get_prgname(), set_value_arg); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } } else if ( g_strcmp0(set_property_arg, "DiscoverableTimeout") == 0 || g_strcmp0(set_property_arg, "PairableTimeout") == 0 ) { v = g_variant_new_uint32((guint32) atoi(set_value_arg)); } else { g_print("%s: Invalid property: %s\n", g_get_prgname(), set_property_arg); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } GVariant *props = adapter_get_properties(adapter, &error); exit_if_error(error); if(g_ascii_strcasecmp(set_property_arg, "Alias") == 0) adapter_set_alias(adapter, g_variant_get_string(v, NULL), &error); else if(g_ascii_strcasecmp(set_property_arg, "Discoverable") == 0) adapter_set_discoverable(adapter, g_variant_get_boolean(v), &error); else if(g_ascii_strcasecmp(set_property_arg, "DiscoverableTimeout") == 0) adapter_set_discoverable_timeout(adapter, g_variant_get_uint32(v), &error); else if(g_ascii_strcasecmp(set_property_arg, "Pairable") == 0) adapter_set_pairable(adapter, g_variant_get_boolean(v), &error); else if(g_ascii_strcasecmp(set_property_arg, "PairableTimeout") == 0) adapter_set_pairable_timeout(adapter, g_variant_get_uint32(v), &error); else if(g_ascii_strcasecmp(set_property_arg, "Powered") == 0) adapter_set_powered(adapter, g_variant_get_boolean(v), &error); exit_if_error(error); GVariant *old_value = g_variant_lookup_value(props, set_property_arg, NULL); g_assert(old_value != NULL); if (g_variant_type_equal(G_VARIANT_TYPE_STRING, g_variant_get_type(old_value))) { g_print("%s: %s -> %s\n", set_property_arg, g_variant_get_string(old_value, NULL), g_variant_get_string(v, NULL)); } else if (g_variant_type_equal(G_VARIANT_TYPE_BOOLEAN, g_variant_get_type(old_value))) { g_print("%s: %u -> %u\n", set_property_arg, g_variant_get_boolean(old_value), g_variant_get_boolean(v)); } else if (g_variant_type_equal(G_VARIANT_TYPE_UINT32, g_variant_get_type(old_value))) { g_print("%s: %u -> %u\n", set_property_arg, g_variant_get_uint32(old_value), g_variant_get_uint32(v)); } g_variant_unref(props); // g_variant_unref(v); /* Floating references do not need to be unref */ g_object_unref(adapter); } g_object_unref(manager); dbus_disconnect(); exit(EXIT_SUCCESS); } bluez-tools-2.0~20170911.0.7cb788c/src/bt-agent.1000066400000000000000000000132101315563672100204570ustar00rootroot00000000000000.\" Automatically generated by Pod::Man 2.27 (Pod::Simple 3.28) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is turned on, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{ . if \nF \{ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" .\" Accent mark definitions (@(#)ms.acc 1.5 88/02/08 SMI; from UCB 4.2). .\" Fear. Run. Save yourself. No user-serviceable parts. . \" fudge factors for nroff and troff .if n \{\ . ds #H 0 . ds #V .8m . ds #F .3m . ds #[ \f1 . ds #] \fP .\} .if t \{\ . ds #H ((1u-(\\\\n(.fu%2u))*.13m) . ds #V .6m . ds #F 0 . ds #[ \& . ds #] \& .\} . \" simple accents for nroff and troff .if n \{\ . ds ' \& . ds ` \& . ds ^ \& . ds , \& . ds ~ ~ . ds / .\} .if t \{\ . ds ' \\k:\h'-(\\n(.wu*8/10-\*(#H)'\'\h"|\\n:u" . ds ` \\k:\h'-(\\n(.wu*8/10-\*(#H)'\`\h'|\\n:u' . ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'^\h'|\\n:u' . ds , \\k:\h'-(\\n(.wu*8/10)',\h'|\\n:u' . ds ~ \\k:\h'-(\\n(.wu-\*(#H-.1m)'~\h'|\\n:u' . ds / \\k:\h'-(\\n(.wu*8/10-\*(#H)'\z\(sl\h'|\\n:u' .\} . \" troff and (daisy-wheel) nroff accents .ds : \\k:\h'-(\\n(.wu*8/10-\*(#H+.1m+\*(#F)'\v'-\*(#V'\z.\h'.2m+\*(#F'.\h'|\\n:u'\v'\*(#V' .ds 8 \h'\*(#H'\(*b\h'-\*(#H' .ds o \\k:\h'-(\\n(.wu+\w'\(de'u-\*(#H)/2u'\v'-.3n'\*(#[\z\(de\v'.3n'\h'|\\n:u'\*(#] .ds d- \h'\*(#H'\(pd\h'-\w'~'u'\v'-.25m'\f2\(hy\fP\v'.25m'\h'-\*(#H' .ds D- D\\k:\h'-\w'D'u'\v'-.11m'\z\(hy\v'.11m'\h'|\\n:u' .ds th \*(#[\v'.3m'\s+1I\s-1\v'-.3m'\h'-(\w'I'u*2/3)'\s-1o\s+1\*(#] .ds Th \*(#[\s+2I\s-2\h'-\w'I'u*3/5'\v'-.3m'o\v'.3m'\*(#] .ds ae a\h'-(\w'a'u*4/10)'e .ds Ae A\h'-(\w'A'u*4/10)'E . \" corrections for vroff .if v .ds ~ \\k:\h'-(\\n(.wu*9/10-\*(#H)'\s-2\u~\d\s+2\h'|\\n:u' .if v .ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'\v'-.4m'^\v'.4m'\h'|\\n:u' . \" for low resolution devices (crt and lpr) .if \n(.H>23 .if \n(.V>19 \ \{\ . ds : e . ds 8 ss . ds o a . ds d- d\h'-1'\(ga . ds D- D\h'-1'\(hy . ds th \o'bp' . ds Th \o'LP' . ds ae ae . ds Ae AE .\} .rm #[ #] #H #V #F C .\" ======================================================================== .\" .IX Title "bt-agent 1" .TH bt-agent 1 "2014-08-03" "" "bluez-tools" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" bt\-adapter \- a bluetooth agent .SH "SYNOPSIS" .IX Header "SYNOPSIS" bt-agent [\s-1OPTION...\s0] .PP Help Options: \-h, \-\-help .PP Application Options: \-c, \-\-capability= \-p, \-\-pin \-d, \-\-daemon .SH "DESCRIPTION" .IX Header "DESCRIPTION" This interactive utility is used to manage incoming Bluetooth requests (eg. request of pincode, request of authorize a connection/service request, etc). .SH "OPTIONS" .IX Header "OPTIONS" \&\fB\-h, \-\-help\fR Show help .PP \&\fB\-c, \-\-capability \fR Specify the input and output capabilities of the agent. `capability` can be one of: DisplayOnly DisplayYesNo (default) KeyboardOnly NoInputNoOutput (if this option does not defined \- `DisplayYesNo' will be used) .PP \&\fB\-p, \-\-pin Use a file that holds a list of authorization codes for each device by name or mac address. The contents of the file should be in this format: \s-1AA:BB:CC:DD:EE:FF 123456 \s0 RemoteDeviceName * (accept any pin code) If a pin file is included, it will check the passkey of the pairing device against the key included in the file. It will automatically authorize the device if the key matches, otherwise it will request the user for manual authorization. .PP \&\fB\-d, \-\-daemon\fR Run the agent as a background process (as a daemon). The agent will rely on a pin file and request no manual user authorization. Any devices that attempt to pair without a valid passkey defined in the pin file will be automatically rejected. .SH "AUTHOR" .IX Header "AUTHOR" Alexander Orlenko . .SH "SEE ALSO" .IX Header "SEE ALSO" \&\fIbt\-adapter\fR\|(1) \fIbt\-device\fR\|(1) \fIbt\-network\fR\|(1) bluez-tools-2.0~20170911.0.7cb788c/src/bt-agent.c000066400000000000000000000172451315563672100205550ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010-2011 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include #include #include #include #include #include "lib/dbus-common.h" #include "lib/helpers.h" #include "lib/agent-helper.h" #include "lib/bluez-api.h" static gboolean need_unregister = TRUE; static GMainLoop *mainloop = NULL; static GHashTable *pin_hash_table = NULL; static gchar *pin_arg = NULL; // Not touching this for now. It seems to work. static void _read_pin_file(const gchar *filename, GHashTable *pin_hash_table, gboolean first_run) { g_assert(filename != NULL && strlen(filename) > 0); g_assert(pin_hash_table != NULL); GStatBuf sbuf; memset(&sbuf, 0, sizeof(sbuf)); if (g_stat(filename, &sbuf) != 0) { if (first_run) { g_printerr("%s: %s\n", filename, strerror(errno)); exit(EXIT_FAILURE); } else { return; } } if (!S_ISREG(sbuf.st_mode)) { if (first_run) { g_printerr("%s: It's not a regular file\n", filename); exit(EXIT_FAILURE); } else { return; } } if (sbuf.st_mode & S_IROTH) { if (first_run) g_print("Warning! %s is world readable!\n", filename); } FILE *fp = g_fopen(filename, "r"); if (!fp) { if (first_run) { g_printerr("%s: %s\n", filename, strerror(errno)); exit(EXIT_FAILURE); } else { return; } } g_hash_table_remove_all(pin_hash_table); gchar *line = NULL; size_t len = 0; ssize_t read; guint n = 0; GRegex *regex = g_regex_new("^(\\S+)\\s+(\\S+)$", 0, 0, NULL); while ((read = getline(&line, &len, fp)) != -1) { n++; if (g_regex_match_simple("^\\s*(#|$)", line, 0, 0)) continue; GMatchInfo *match_info; if (g_regex_match(regex, line, 0, &match_info)) { gchar **t = g_match_info_fetch_all(match_info); /* Convert MAC to upper case */ if (g_regex_match_simple("^([0-9a-fA-F]{2}(:|$)){6}$", t[1], 0, 0)) g_hash_table_insert(pin_hash_table, g_ascii_strup(t[1], -1), g_strdup(t[2])); else g_hash_table_insert(pin_hash_table, g_strdup(t[1]), g_strdup(t[2])); g_strfreev(t); } else { if (first_run) g_print("%d: Invalid line (ignored)\n", n); } g_match_info_free(match_info); } g_regex_unref(regex); if (line) g_free(line); fclose(fp); first_run = FALSE; return; } static gboolean usr1_signal_handler(gpointer data) { g_message("SIGUSR1 received"); if (!pin_arg) return G_SOURCE_CONTINUE; /* Re-read PIN's file */ g_print("Re-reading PIN's file\n"); _read_pin_file(pin_arg, pin_hash_table, FALSE); return G_SOURCE_CONTINUE; } static gboolean term_signal_handler(gpointer data) { if (g_main_loop_is_running(mainloop)) g_main_loop_quit(mainloop); return G_SOURCE_REMOVE; } static gchar *capability_arg = NULL; static gboolean daemon_arg = FALSE; static GOptionEntry entries[] = { {"capability", 'c', 0, G_OPTION_ARG_STRING, &capability_arg, "Agent capability", ""}, {"pin", 'p', 0, G_OPTION_ARG_STRING, &pin_arg, "Path to the PIN's file"}, {"daemon", 'd', 0, G_OPTION_ARG_NONE, &daemon_arg, "Run in background (as daemon)"}, {NULL} }; int main(int argc, char *argv[]) { GError *error = NULL; GOptionContext *context; /* Query current locale */ setlocale(LC_CTYPE, ""); // Deprecated // g_type_init(); dbus_init(); context = g_option_context_new(" - a bluetooth agent"); g_option_context_add_main_entries(context, entries, NULL); g_option_context_set_summary(context, "Version "PACKAGE_VERSION); g_option_context_set_description(context, "`capability` can be one of:\n" " DisplayOnly\n" " DisplayYesNo (default)\n" " KeyboardOnly\n" " NoInputNoOutput\n\n" "Report bugs to <"PACKAGE_BUGREPORT">." "Project home page <"PACKAGE_URL">." ); if (!g_option_context_parse(context, &argc, &argv, &error)) { g_print("%s: %s\n", g_get_prgname(), error->message); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } if (capability_arg) { if ( g_strcmp0(capability_arg, "DisplayOnly") != 0 && g_strcmp0(capability_arg, "DisplayYesNo") != 0 && g_strcmp0(capability_arg, "KeyboardOnly") != 0 && g_strcmp0(capability_arg, "NoInputNoOutput") != 0 ) { g_print("%s: Invalid capability: %s\n", g_get_prgname(), capability_arg); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } } else { capability_arg = "DisplayYesNo"; // default value } g_option_context_free(context); if (!dbus_system_connect(&error)) { g_printerr("Couldn't connect to DBus system bus: %s\n", error->message); exit(EXIT_FAILURE); } /* Check, that bluetooth daemon is running */ if (!intf_supported(BLUEZ_DBUS_SERVICE_NAME, MANAGER_DBUS_PATH, MANAGER_DBUS_INTERFACE)) { g_printerr("%s: bluez service is not found\n", g_get_prgname()); g_printerr("Did you forget to run bluetoothd?\n"); exit(EXIT_FAILURE); } /* Read PIN's file */ if (pin_arg) { pin_hash_table = g_hash_table_new_full(g_str_hash, g_str_equal, g_free, g_free); _read_pin_file(pin_arg, pin_hash_table, TRUE); } mainloop = g_main_loop_new(NULL, FALSE); Manager *manager = g_object_new(MANAGER_TYPE, NULL); AgentManager *agent_manager = agent_manager_new(); if(daemon_arg) register_agent_callbacks(FALSE, pin_hash_table, mainloop, &error); else register_agent_callbacks(TRUE, pin_hash_table, mainloop, &error); exit_if_error(error); agent_manager_register_agent(agent_manager, AGENT_PATH, capability_arg, &error); exit_if_error(error); g_print("Agent registered\n"); agent_manager_request_default_agent(agent_manager, AGENT_PATH, &error); exit_if_error(error); g_print("Default agent requested\n"); if (daemon_arg) { pid_t pid, sid; /* Fork off the parent process */ pid = fork(); if (pid < 0) exit(EXIT_FAILURE); /* Ok, terminate parent proccess */ if (pid > 0) exit(EXIT_SUCCESS); /* Create a new SID for the child process */ sid = setsid(); if (sid < 0) exit(EXIT_FAILURE); /* Close out the standard file descriptors */ close(STDIN_FILENO); close(STDOUT_FILENO); close(STDERR_FILENO); } /* Add SIGTERM/SIGINT/SIGUSR1 handlers */ g_unix_signal_add (SIGTERM, usr1_signal_handler, NULL); g_unix_signal_add (SIGINT, term_signal_handler, NULL); g_unix_signal_add (SIGUSR1, term_signal_handler, NULL); g_main_loop_run(mainloop); if (need_unregister) { g_print("unregistering agent...\n"); agent_manager_unregister_agent(agent_manager, AGENT_PATH, &error); exit_if_error(error); } g_main_loop_unref(mainloop); unregister_agent_callbacks(NULL); g_object_unref(agent_manager); g_object_unref(manager); dbus_disconnect(); exit(EXIT_SUCCESS); } bluez-tools-2.0~20170911.0.7cb788c/src/bt-device.1000066400000000000000000000163531315563672100206330ustar00rootroot00000000000000.\" Automatically generated by Pod::Man 2.27 (Pod::Simple 3.28) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is turned on, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{ . if \nF \{ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" .\" Accent mark definitions (@(#)ms.acc 1.5 88/02/08 SMI; from UCB 4.2). .\" Fear. Run. Save yourself. No user-serviceable parts. . \" fudge factors for nroff and troff .if n \{\ . ds #H 0 . ds #V .8m . ds #F .3m . ds #[ \f1 . ds #] \fP .\} .if t \{\ . ds #H ((1u-(\\\\n(.fu%2u))*.13m) . ds #V .6m . ds #F 0 . ds #[ \& . ds #] \& .\} . \" simple accents for nroff and troff .if n \{\ . ds ' \& . ds ` \& . ds ^ \& . ds , \& . ds ~ ~ . ds / .\} .if t \{\ . ds ' \\k:\h'-(\\n(.wu*8/10-\*(#H)'\'\h"|\\n:u" . ds ` \\k:\h'-(\\n(.wu*8/10-\*(#H)'\`\h'|\\n:u' . ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'^\h'|\\n:u' . ds , \\k:\h'-(\\n(.wu*8/10)',\h'|\\n:u' . ds ~ \\k:\h'-(\\n(.wu-\*(#H-.1m)'~\h'|\\n:u' . ds / \\k:\h'-(\\n(.wu*8/10-\*(#H)'\z\(sl\h'|\\n:u' .\} . \" troff and (daisy-wheel) nroff accents .ds : \\k:\h'-(\\n(.wu*8/10-\*(#H+.1m+\*(#F)'\v'-\*(#V'\z.\h'.2m+\*(#F'.\h'|\\n:u'\v'\*(#V' .ds 8 \h'\*(#H'\(*b\h'-\*(#H' .ds o \\k:\h'-(\\n(.wu+\w'\(de'u-\*(#H)/2u'\v'-.3n'\*(#[\z\(de\v'.3n'\h'|\\n:u'\*(#] .ds d- \h'\*(#H'\(pd\h'-\w'~'u'\v'-.25m'\f2\(hy\fP\v'.25m'\h'-\*(#H' .ds D- D\\k:\h'-\w'D'u'\v'-.11m'\z\(hy\v'.11m'\h'|\\n:u' .ds th \*(#[\v'.3m'\s+1I\s-1\v'-.3m'\h'-(\w'I'u*2/3)'\s-1o\s+1\*(#] .ds Th \*(#[\s+2I\s-2\h'-\w'I'u*3/5'\v'-.3m'o\v'.3m'\*(#] .ds ae a\h'-(\w'a'u*4/10)'e .ds Ae A\h'-(\w'A'u*4/10)'E . \" corrections for vroff .if v .ds ~ \\k:\h'-(\\n(.wu*9/10-\*(#H)'\s-2\u~\d\s+2\h'|\\n:u' .if v .ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'\v'-.4m'^\v'.4m'\h'|\\n:u' . \" for low resolution devices (crt and lpr) .if \n(.H>23 .if \n(.V>19 \ \{\ . ds : e . ds 8 ss . ds o a . ds d- d\h'-1'\(ga . ds D- D\h'-1'\(hy . ds th \o'bp' . ds Th \o'LP' . ds ae ae . ds Ae AE .\} .rm #[ #] #H #V #F C .\" ======================================================================== .\" .IX Title "bt-device 1" .TH bt-device 1 "2014-08-01" "" "bluez-tools" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" bt\-device \- a bluetooth device manager .SH "SYNOPSIS" .IX Header "SYNOPSIS" bt-device [\s-1OPTION...\s0] .PP Help Options: \-h, \-\-help .PP Application Options: \-a, \-\-adapter= \-l, \-\-list \-c, \-\-connect= \-d, \-\-disconnect= \-r, \-\-remove= \-i, \-\-info= \-s, \-\-services [] \-\-set \-v, \-\-verbose .SH "DESCRIPTION" .IX Header "DESCRIPTION" This utility is used to manage Bluetooth devices. You can list added devices, connect to a new device, disconnect device, remove added device, show info about device, discover remote device services or change device properties. .SH "OPTIONS" .IX Header "OPTIONS" \&\fB\-h, \-\-help\fR Show help .PP \&\fB\-a, \-\-adapter \fR Specify adapter to use by his Name or \s-1MAC\s0 address (if this option does not defined \- default adapter used) .PP \&\fB\-l, \-\-list\fR List added devices .PP \&\fB\-c, \-\-connect \fR Connect to the remote device by his \s-1MAC,\s0 retrieve all \s-1SDP \s0 records and then initiate the pairing .PP \&\fB\-d, \-\-disconnect \fR Disconnects a specific remote device by terminating the low-level \s-1ACL\s0 connection. .PP \&\fB\-r, \-\-remove\fR Remove device (and also the pairing information) .PP \&\fB\-i, \-\-info\fR Show information about device (returns all properties) .PP \&\fB\-s, \-\-services []\fR Starts the service discovery to retrieve remote service records, the `pattern` parameter can be used to specify specific UUIDs .PP \&\fB\-\-set \fR Change device properties (see \s-1DEVICE PROPERTIES\s0 section for list of available properties) .PP \&\fB\-v, \-\-verbose\fR Verbosely display remote service records (affect to service discovery mode) .SH "DEVICE PROPERTIES" .IX Header "DEVICE PROPERTIES" string Address [ro] The Bluetooth device address (\s-1MAC\s0) of the remote device. .PP string Name [ro] The Bluetooth remote device name. .PP string Icon [ro] Proposed icon name according to the freedesktop.org icon naming specification. .PP uint32 Class [ro] The Bluetooth class of device of the remote device. .PP list UUIDs [ro] List of 128\-bit UUIDs that represents the available remote services. .PP boolean Paired [ro] Indicates if the remote device is paired. .PP boolean Connected [ro] Indicates if the remote device is currently connected. .PP boolean Trusted [rw] Indicates if the remote is seen as trusted. .PP boolean Blocked [rw] If set to true any incoming connections from the device will be immediately rejected. .PP string Alias [rw] The name alias for the remote device. The alias can be used to have a different friendly name for the remote device. .PP .Vb 3 \& In case no alias is set, it will return the remote \& device name. Setting an empty string as alias will \& convert it back to the remote device name. .Ve .PP boolean LegacyPairing [ro] Set to true if the device only supports the pre\-2.1 pairing mechanism. .SH "AUTHOR" .IX Header "AUTHOR" Alexander Orlenko . .SH "SEE ALSO" .IX Header "SEE ALSO" \&\fIbt\-adapter\fR\|(1) \fIbt\-agent\fR\|(1) \fIbt\-network\fR\|(1) bluez-tools-2.0~20170911.0.7cb788c/src/bt-device.c000066400000000000000000000610601315563672100207100ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include #include #include "lib/dbus-common.h" #include "lib/helpers.h" #include "lib/agent-helper.h" #include "lib/sdp.h" #include "lib/bluez-api.h" enum { REC, ATTR, SEQ, ELEM, ATTR_ID, UUID_ID, LAST_E }; static int xml_t[LAST_E] = {0, 0, 0, 0, -1, -1}; /* Main arguments */ static gchar *adapter_arg = NULL; static gboolean list_arg = FALSE; static gchar *connect_arg = NULL; static gchar *disconnect_arg = NULL; static gchar *remove_arg = NULL; static gchar *info_arg = NULL; static gboolean services_arg = FALSE; static gchar *services_device_arg = NULL; static gchar *services_pattern_arg = NULL; static gboolean set_arg = FALSE; static gchar *set_device_arg = NULL; static gchar *set_property_arg = NULL; static gchar *set_value_arg = NULL; static gboolean verbose_arg = FALSE; static gboolean is_verbose_attr(int attr_id) { if ( attr_id == SDP_ATTR_ID_SERVICE_CLASS_ID_LIST || attr_id == SDP_ATTR_ID_PROTOCOL_DESCRIPTOR_LIST || attr_id == SDP_ATTR_ID_BLUETOOTH_PROFILE_DESCRIPTOR_LIST || attr_id == SDP_ATTR_ID_DOCUMENTATION_URL || attr_id == SDP_ATTR_ID_SERVICE_NAME || attr_id == SDP_ATTR_ID_SERVICE_DESCRIPTION || attr_id == SDP_ATTR_ID_PROVIDER_NAME || attr_id == SDP_ATTR_ID_SECURITY_DESCRIPTION ) return FALSE; return TRUE; } static const gchar *xml_get_attr_value(const gchar *attr_name, const gchar **attribute_names, const gchar **attribute_values) { for (int i = 0; attribute_names[i] != NULL; i++) { if (g_strcmp0(attribute_names[i], attr_name) == 0) { return attribute_values[i]; } } return NULL; } static void xml_start_element(GMarkupParseContext *context, const gchar *element_name, const gchar **attribute_names, const gchar **attribute_values, gpointer user_data, GError **error) { const gchar *id_t = xml_get_attr_value("id", attribute_names, attribute_values); const gchar *value_t = xml_get_attr_value("value", attribute_names, attribute_values); if (g_strcmp0(element_name, "record") == 0) { xml_t[REC]++; } else if (g_strcmp0(element_name, "attribute") == 0 && id_t) { int attr_id = xtoi(id_t); const gchar *attr_name = sdp_get_attr_id_name(attr_id); xml_t[ATTR]++; xml_t[ATTR_ID] = attr_id; if (!verbose_arg && is_verbose_attr(xml_t[ATTR_ID])) return; if (attr_name == NULL) { g_print("AttrID-%s: ", id_t); } else { g_print("%s: ", attr_name); } } else if (g_strcmp0(element_name, "sequence") == 0) { xml_t[SEQ]++; } else if (g_pattern_match_simple("*int*", element_name) && value_t) { xml_t[ELEM]++; if (!verbose_arg && is_verbose_attr(xml_t[ATTR_ID])) return; if (xml_t[ELEM] == 1 && xml_t[SEQ] > 1) { g_print("\n"); for (int i = 0; i < xml_t[SEQ]; i++) g_print(" "); } else if (xml_t[ELEM] > 1) { g_print(", "); } if (xml_t[UUID_ID] == SDP_UUID_RFCOMM) { g_print("Channel: %d", xtoi(value_t)); } else { g_print("0x%x", xtoi(value_t)); } } else if (g_strcmp0(element_name, "uuid") == 0 && value_t) { int uuid_id = -1; const gchar *uuid_name; if (value_t[0] == '0' && value_t[1] == 'x') { uuid_id = xtoi(value_t); uuid_name = sdp_get_uuid_name(uuid_id); } else { uuid_name = uuid2name(value_t); } xml_t[ELEM]++; xml_t[UUID_ID] = uuid_id; if (!verbose_arg && is_verbose_attr(xml_t[ATTR_ID])) return; if (xml_t[ELEM] == 1 && xml_t[SEQ] > 1) { g_print("\n"); for (int i = 0; i < xml_t[SEQ]; i++) g_print(" "); } else if (xml_t[ELEM] > 1) { g_print(", "); } if (uuid_name == NULL) { g_print("\"UUID-%s\"", value_t); } else { g_print("\"%s\"", uuid_name); } } else if (g_strcmp0(element_name, "text") == 0 && value_t) { xml_t[ELEM]++; if (!verbose_arg && is_verbose_attr(xml_t[ATTR_ID])) return; if (xml_t[ELEM] == 1 && xml_t[SEQ] > 1) { g_print("\n"); for (int i = 0; i < xml_t[SEQ]; i++) g_print(" "); } else if (xml_t[ELEM] > 1) { g_print(", "); } g_print("\"%s\"", value_t); } else if (g_strcmp0(element_name, "boolean") == 0 && value_t) { xml_t[ELEM]++; if (!verbose_arg && is_verbose_attr(xml_t[ATTR_ID])) return; if (xml_t[ELEM] == 1 && xml_t[SEQ] > 1) { g_print("\n"); for (int i = 0; i < xml_t[SEQ]; i++) g_print(" "); } else if (xml_t[ELEM] > 1) { g_print(", "); } g_print("%s", value_t); } else { if (error) *error = g_error_new(G_MARKUP_ERROR, G_MARKUP_ERROR_UNKNOWN_ELEMENT, "Invalid XML element: %s", element_name); } } static void xml_end_element(GMarkupParseContext *context, const gchar *element_name, gpointer user_data, GError **error) { if (g_strcmp0(element_name, "record") == 0) { xml_t[ATTR] = 0; xml_t[SEQ] = 0; xml_t[ELEM] = 0; xml_t[ATTR_ID] = -1; xml_t[UUID_ID] = -1; } else if (g_strcmp0(element_name, "attribute") == 0) { xml_t[SEQ] = 0; xml_t[ELEM] = 0; int old_attr_id = xml_t[ATTR_ID]; xml_t[ATTR_ID] = -1; xml_t[UUID_ID] = -1; if (!verbose_arg && is_verbose_attr(old_attr_id)) return; g_print("\n"); } else if (g_strcmp0(element_name, "sequence") == 0) { xml_t[SEQ]--; xml_t[ELEM] = 0; xml_t[UUID_ID] = -1; } } static void create_paired_device_done(gpointer data) { g_assert(data != NULL); GMainLoop *mainloop = data; g_main_loop_quit(mainloop); } static void _bt_device_pair_callback(GObject *source_object, GAsyncResult *res, gpointer user_data) { g_assert(user_data != NULL); GHashTable *dict = (GHashTable *) user_data; Device *device = (Device *) g_hash_table_lookup(dict, "device"); GError *error = NULL; device_pair_finish(device, res, &error); exit_if_error(error); GMainLoop *mainloop = (GMainLoop *) g_hash_table_lookup(dict, "mainloop"); g_main_loop_quit(mainloop); } static GHashTable *_bt_device_sdp_browse(const gchar *device_path, const gchar *pattern) { int pipefd[2]; pipe(pipefd); // Fork the process into a child process to make an exec call int pid = fork(); // Child (to call sdptool) if (pid == 0) { // close reading end in the child close(pipefd[0]); // send stdout to the pipe dup2(pipefd[1], 1); // send stderr to the pipe dup2(pipefd[1], 2); // this descriptor is no longer needed close(pipefd[1]); if(!g_file_test ("/bin/sdptool", G_FILE_TEST_EXISTS)) { write(2, "sdptool not found\n", sizeof("sdptool not found\n")); exit(EXIT_FAILURE); } if(pattern == NULL || strlen(pattern) == 0) execl("/bin/sdptool", "/bin/sdptool", "browse", "--xml", device_path, (char *) 0); else execl("/bin/sdptool", "/bin/sdptool", "browse", "--xml", "--uuid", pattern, device_path, (char *) 0); } if(pid == -1) { perror("forking process failed"); exit(EXIT_FAILURE); } close(pipefd[1]); // close the write end of the pipe in the parent GInputStream *exec_output = (GInputStream *) g_unix_input_stream_new(pipefd[0], TRUE); GDataInputStream *exec_data_input_stream = g_data_input_stream_new(exec_output); GPtrArray *array = g_ptr_array_new(); guint record_counter = 0; guint n = 0; GError *error = NULL; GString *string_buffer = g_string_new(""); while(TRUE) { n++; gchar *line = g_data_input_stream_read_line_utf8(exec_data_input_stream, NULL, NULL, &error); exit_if_error(error); // If there is no content, then break out of the loop if(!line) break; if(n == 1) { if(g_regex_match_simple("Failed", line, 0, 0) || g_regex_match_simple("Error", line, 0, 0)) { g_print("%s\n", line); exit(EXIT_FAILURE); } else if(g_regex_match_simple("not found", line, 0, 0)) { g_print("Failed to start SDP discovery. Please make sure you have bluez-utils installed on your system.\n"); exit(EXIT_FAILURE); } continue; } if(g_regex_match_simple("<\\?xml(.*)\\?>", line, 0, 0)) { if(record_counter != 0) { g_ptr_array_add(array, g_string_free(string_buffer, FALSE)); string_buffer = g_string_new(""); } record_counter++; } g_string_append(string_buffer, line); } g_ptr_array_add(array, g_string_free(string_buffer, FALSE)); GHashTable *sdp_hash_table = g_hash_table_new(g_int_hash, g_int_equal); int i = 0; for(i = 0; i < array->len; i++) { GRegex *record_id_regex = g_regex_new("(\\s*\\s)", G_REGEX_CASELESS | G_REGEX_MULTILINE | G_REGEX_NEWLINE_ANYCRLF, 0, &error); exit_if_error(error); GMatchInfo *match_info; g_regex_match (record_id_regex, (gchar *) g_ptr_array_index(array, i), 0, &match_info); if(g_match_info_matches(match_info)) { gchar *word = g_match_info_fetch(match_info, 2); guint32 *key = g_new(guint32, 1); *key = 0; sscanf(word, "0x%x", key); g_hash_table_insert(sdp_hash_table, key, (gchar *) g_ptr_array_index(array, i)); g_free(word); } g_match_info_free(match_info); g_regex_unref(record_id_regex); } g_input_stream_close(exec_output, NULL, &error); exit_if_error(error); g_object_unref(exec_data_input_stream); g_object_unref(exec_output); g_ptr_array_unref(array); return sdp_hash_table; } static GOptionEntry entries[] = { {"adapter", 'a', 0, G_OPTION_ARG_STRING, &adapter_arg, "Adapter Name or MAC", ""}, {"list", 'l', 0, G_OPTION_ARG_NONE, &list_arg, "List added devices", NULL}, {"connect", 'c', 0, G_OPTION_ARG_STRING, &connect_arg, "Connect to the remote device", ""}, {"disconnect", 'd', 0, G_OPTION_ARG_STRING, &disconnect_arg, "Disconnect the remote device", ""}, {"remove", 'r', 0, G_OPTION_ARG_STRING, &remove_arg, "Remove device", ""}, {"info", 'i', 0, G_OPTION_ARG_STRING, &info_arg, "Get info about device", ""}, {"services", 's', 0, G_OPTION_ARG_NONE, &services_arg, "Discover device services", NULL}, {"set", 0, 0, G_OPTION_ARG_NONE, &set_arg, "Set device property", NULL}, {"verbose", 'v', 0, G_OPTION_ARG_NONE, &verbose_arg, "Verbosely display remote service records", NULL}, {NULL} }; int main(int argc, char *argv[]) { GError *error = NULL; GOptionContext *context; /* Query current locale */ setlocale(LC_CTYPE, ""); /* Deprecated */ // g_type_init(); dbus_init(); context = g_option_context_new("- a bluetooth device manager"); g_option_context_add_main_entries(context, entries, NULL); g_option_context_set_summary(context, "Version "PACKAGE_VERSION); g_option_context_set_description(context, "Services Options:\n" " -s, --services []\n" " Where `pattern` is an optional specific UUID to search\n\n" "Set Options:\n" " --set \n" " Where\n" " `name|mac` is a device Name or MAC\n" " `property` is one of:\n" " Alias\n" " Trusted\n" " Blocked\n\n" "Report bugs to <"PACKAGE_BUGREPORT">." "Project home page <"PACKAGE_URL">." ); if (!g_option_context_parse(context, &argc, &argv, &error)) { g_print("%s: %s\n", g_get_prgname(), error->message); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } else if (!list_arg && (!connect_arg || strlen(connect_arg) == 0) && (!disconnect_arg || strlen(disconnect_arg) == 0) && (!remove_arg || strlen(remove_arg) == 0) && (!info_arg || strlen(info_arg) == 0) && !services_arg && !set_arg) { g_print("%s", g_option_context_get_help(context, FALSE, NULL)); exit(EXIT_FAILURE); } else if (services_arg && (argc != 2 || strlen(argv[1]) == 0) && (argc != 3 || strlen(argv[1]) == 0)) { g_print("%s: Invalid arguments for --services\n", g_get_prgname()); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } else if (set_arg && (argc != 4 || strlen(argv[1]) == 0 || strlen(argv[2]) == 0 || strlen(argv[3]) == 0)) { g_print("%s: Invalid arguments for --set\n", g_get_prgname()); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } g_option_context_free(context); if (!dbus_system_connect(&error)) { g_printerr("Couldn't connect to DBus system bus: %s\n", error->message); exit(EXIT_FAILURE); } /* Check, that bluetooth daemon is running */ if (!intf_supported(BLUEZ_DBUS_SERVICE_NAME, MANAGER_DBUS_PATH, MANAGER_DBUS_INTERFACE)) { g_printerr("%s: bluez service is not found\n", g_get_prgname()); g_printerr("Did you forget to run bluetoothd?\n"); exit(EXIT_FAILURE); } Manager *manager = manager_new(); Adapter *adapter = find_adapter(adapter_arg, &error); exit_if_error(error); if (list_arg) { const gchar **devices_list = manager_get_devices(manager, adapter_get_dbus_object_path(adapter)); if (devices_list == NULL) { g_print("No devices found\n"); exit(EXIT_FAILURE); } g_print("Added devices:\n"); const gchar **devices = NULL; for (devices = devices_list; *devices != NULL; devices++) { const gchar *device_path = *devices; Device *device = device_new(device_path); g_print("%s (%s)\n", device_get_alias(device, &error), device_get_address(device, &error)); exit_if_error(error); g_object_unref(device); } } else if (connect_arg) { g_print("Connecting to: %s\n", connect_arg); GMainLoop *mainloop = g_main_loop_new(NULL, FALSE); AgentManager *agent_manager = agent_manager_new(); agent_need_unregister = TRUE; register_agent_callbacks(TRUE, NULL, mainloop, &error); exit_if_error(error); agent_manager_register_agent(agent_manager, AGENT_PATH, "DisplayYesNo", &error); exit_if_error(error); Device *device = find_device(adapter, connect_arg, &error); exit_if_error(error); if(!device) { g_printerr("Error: Device not found.\n"); exit(EXIT_FAILURE); } GHashTable *user_data_hash = g_hash_table_new(g_str_hash, g_str_equal); g_hash_table_insert(user_data_hash, "device", device); g_hash_table_insert(user_data_hash, "mainloop", mainloop); device_pair_async(device, (GAsyncReadyCallback) _bt_device_pair_callback, (gpointer) user_data_hash); g_main_loop_run(mainloop); g_print("Done\n"); g_hash_table_unref(user_data_hash); g_main_loop_unref(mainloop); g_object_unref(device); unregister_agent_callbacks(&error); } else if (disconnect_arg) { Device *device = find_device(adapter, disconnect_arg, &error); exit_if_error(error); if(!device) { g_printerr("Error: Device not found.\n"); exit(EXIT_FAILURE); } g_print("Disconnecting: %s\n", disconnect_arg); device_disconnect(device, &error); exit_if_error(error); g_print("Done\n"); g_object_unref(device); } else if (remove_arg) { Device *device = find_device(adapter, remove_arg, &error); exit_if_error(error); if(!device) { g_printerr("Error: Device not found.\n"); exit(EXIT_FAILURE); } adapter_remove_device(adapter, device_get_dbus_object_path(device), &error); exit_if_error(error); g_print("Done\n"); g_object_unref(device); } else if (info_arg) { Device *device = find_device(adapter, info_arg, &error); exit_if_error(error); if(!device) { g_printerr("Error: Device not found.\n"); exit(EXIT_FAILURE); } g_print("[%s]\n", device_get_address(device, &error)); g_print(" Name: %s\n", device_get_name(device, &error)); g_print(" Alias: %s [rw]\n", device_get_alias(device, &error)); g_print(" Address: %s\n", device_get_address(device, &error)); g_print(" Icon: %s\n", device_get_icon(device, &error)); g_print(" Class: 0x%x\n", device_get_class(device, &error)); g_print(" Paired: %d\n", device_get_paired(device, &error)); g_print(" Trusted: %d [rw]\n", device_get_trusted(device, &error)); g_print(" Blocked: %d [rw]\n", device_get_blocked(device, &error)); g_print(" Connected: %d\n", device_get_connected(device, &error)); g_print(" UUIDs: ["); const gchar **uuids = device_get_uuids(device, &error); for (int j = 0; uuids[j] != NULL; j++) { if (j > 0) g_print(", "); g_print("%s", uuid2name(uuids[j])); } g_print("]\n"); g_object_unref(device); } else if (services_arg) { services_device_arg = argv[1]; if (argc == 3) { services_pattern_arg = argv[2]; } Device *device = find_device(adapter, services_device_arg, &error); exit_if_error(error); if(!device) { g_printerr("Error: Device not found.\n"); exit(EXIT_FAILURE); } const gchar *device_address = device_get_address(device, &error); exit_if_error(error); g_print("Discovering services...\n"); // Because BlueZ 5 removed the API call for discover services, we will use sdptool as an alternative // GHashTable *device_services = device_discover_services(device, name2uuid(services_pattern_arg), &error); GHashTable *device_services = _bt_device_sdp_browse(device_address, name2uuid(services_pattern_arg)); exit_if_error(error); GHashTableIter iter; gpointer key, value; g_hash_table_iter_init(&iter, device_services); int n = 0; while (g_hash_table_iter_next(&iter, &key, &value)) { n++; if (n == 1) g_print("\n"); // g_print("[RECORD:%d]\n", (gint) key); g_print("[RECORD:0x%x]\n", *(guint32 *) key); GMarkupParser xml_parser = {xml_start_element, xml_end_element, NULL, NULL, NULL}; GMarkupParseContext *xml_parse_context = g_markup_parse_context_new(&xml_parser, 0, NULL, NULL); g_markup_parse_context_parse(xml_parse_context, value, strlen(value), &error); exit_if_error(error); g_markup_parse_context_free(xml_parse_context); g_print("\n"); } g_print("Done\n"); g_hash_table_unref(device_services); g_object_unref(device); } else if (set_arg) { set_device_arg = argv[1]; set_property_arg = argv[2]; set_value_arg = argv[3]; Device *device = find_device(adapter, set_device_arg, &error); exit_if_error(error); if(!device) { g_printerr("Error: Device not found.\n"); exit(EXIT_FAILURE); } GVariant *v = NULL; if (g_strcmp0(set_property_arg, "Alias") == 0) { v = g_variant_new_string(set_value_arg); } else if ( g_strcmp0(set_property_arg, "Trusted") == 0 || g_strcmp0(set_property_arg, "Blocked") == 0 ) { if (g_strcmp0(set_value_arg, "0") == 0 || g_ascii_strcasecmp(set_value_arg, "FALSE") == 0 || g_ascii_strcasecmp(set_value_arg, "OFF") == 0) { v = g_variant_new_boolean(FALSE); } else if (g_strcmp0(set_value_arg, "1") == 0 || g_ascii_strcasecmp(set_value_arg, "TRUE") == 0 || g_ascii_strcasecmp(set_value_arg, "ON") == 0) { v = g_variant_new_boolean(TRUE); } else { g_print("%s: Invalid boolean value: %s\n", g_get_prgname(), set_value_arg); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } } else { g_print("%s: Invalid property: %s\n", g_get_prgname(), set_property_arg); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } GVariant *props = device_get_properties(device, &error); exit_if_error(error); if(g_ascii_strcasecmp(set_property_arg, "Alias") == 0) device_set_alias(device, g_variant_get_string(v, NULL), &error); else if(g_ascii_strcasecmp(set_property_arg, "Blocked") == 0) device_set_blocked(device, g_variant_get_boolean(v), &error); else if(g_ascii_strcasecmp(set_property_arg, "Trusted") == 0) device_set_trusted(device, g_variant_get_boolean(v), &error); exit_if_error(error); GVariant *old_value = g_variant_lookup_value(props, set_property_arg, NULL); g_assert(old_value != NULL); if (g_variant_type_equal(G_VARIANT_TYPE_STRING, g_variant_get_type(old_value))) { g_print("%s: %s -> %s\n", set_property_arg, g_variant_get_string(old_value, NULL), g_variant_get_string(v, NULL)); } else if (g_variant_type_equal(G_VARIANT_TYPE_BOOLEAN, g_variant_get_type(old_value))) { g_print("%s: %u -> %u\n", set_property_arg, g_variant_get_boolean(old_value), g_variant_get_boolean(v)); } g_variant_unref(props); // g_variant_unref(v); /* Floating references do not need to be unref */ g_object_unref(device); } g_object_unref(adapter); dbus_disconnect(); exit(EXIT_SUCCESS); } bluez-tools-2.0~20170911.0.7cb788c/src/bt-network.1000066400000000000000000000121531315563672100210570ustar00rootroot00000000000000.\" Automatically generated by Pod::Man 2.27 (Pod::Simple 3.28) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is turned on, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{ . if \nF \{ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" .\" Accent mark definitions (@(#)ms.acc 1.5 88/02/08 SMI; from UCB 4.2). .\" Fear. Run. Save yourself. No user-serviceable parts. . \" fudge factors for nroff and troff .if n \{\ . ds #H 0 . ds #V .8m . ds #F .3m . ds #[ \f1 . ds #] \fP .\} .if t \{\ . ds #H ((1u-(\\\\n(.fu%2u))*.13m) . ds #V .6m . ds #F 0 . ds #[ \& . ds #] \& .\} . \" simple accents for nroff and troff .if n \{\ . ds ' \& . ds ` \& . ds ^ \& . ds , \& . ds ~ ~ . ds / .\} .if t \{\ . ds ' \\k:\h'-(\\n(.wu*8/10-\*(#H)'\'\h"|\\n:u" . ds ` \\k:\h'-(\\n(.wu*8/10-\*(#H)'\`\h'|\\n:u' . ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'^\h'|\\n:u' . ds , \\k:\h'-(\\n(.wu*8/10)',\h'|\\n:u' . ds ~ \\k:\h'-(\\n(.wu-\*(#H-.1m)'~\h'|\\n:u' . ds / \\k:\h'-(\\n(.wu*8/10-\*(#H)'\z\(sl\h'|\\n:u' .\} . \" troff and (daisy-wheel) nroff accents .ds : \\k:\h'-(\\n(.wu*8/10-\*(#H+.1m+\*(#F)'\v'-\*(#V'\z.\h'.2m+\*(#F'.\h'|\\n:u'\v'\*(#V' .ds 8 \h'\*(#H'\(*b\h'-\*(#H' .ds o \\k:\h'-(\\n(.wu+\w'\(de'u-\*(#H)/2u'\v'-.3n'\*(#[\z\(de\v'.3n'\h'|\\n:u'\*(#] .ds d- \h'\*(#H'\(pd\h'-\w'~'u'\v'-.25m'\f2\(hy\fP\v'.25m'\h'-\*(#H' .ds D- D\\k:\h'-\w'D'u'\v'-.11m'\z\(hy\v'.11m'\h'|\\n:u' .ds th \*(#[\v'.3m'\s+1I\s-1\v'-.3m'\h'-(\w'I'u*2/3)'\s-1o\s+1\*(#] .ds Th \*(#[\s+2I\s-2\h'-\w'I'u*3/5'\v'-.3m'o\v'.3m'\*(#] .ds ae a\h'-(\w'a'u*4/10)'e .ds Ae A\h'-(\w'A'u*4/10)'E . \" corrections for vroff .if v .ds ~ \\k:\h'-(\\n(.wu*9/10-\*(#H)'\s-2\u~\d\s+2\h'|\\n:u' .if v .ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'\v'-.4m'^\v'.4m'\h'|\\n:u' . \" for low resolution devices (crt and lpr) .if \n(.H>23 .if \n(.V>19 \ \{\ . ds : e . ds 8 ss . ds o a . ds d- d\h'-1'\(ga . ds D- D\h'-1'\(hy . ds th \o'bp' . ds Th \o'LP' . ds ae ae . ds Ae AE .\} .rm #[ #] #H #V #F C .\" ======================================================================== .\" .IX Title "bt-network 1" .TH bt-network 1 "2014-08-01" "" "bluez-tools" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" bt\-network \- a bluetooth network manager .SH "SYNOPSIS" .IX Header "SYNOPSIS" bt-network [\s-1OPTION...\s0] .PP Help Options: \-h, \-\-help .PP Application Options: \-a, \-\-adapter= \-c, \-\-connect \-s, \-\-server .SH "DESCRIPTION" .IX Header "DESCRIPTION" This utility is used to manage network services (client/server). All servers will be automatically unregistered when the application terminates. .SH "OPTIONS" .IX Header "OPTIONS" \&\fB\-h, \-\-help\fR Show help .PP \&\fB\-a, \-\-adapter \fR Specify adapter to use by his Name or \s-1MAC\s0 address (if this option does not defined \- default adapter used) .PP \&\fB\-c, \-\-connect \fR Connect to the network device and return the network interface name, uuid can be either one of \*(L"gn\*(R", \*(L"panu\*(R" or \*(L"nap\*(R" .PP \&\fB\-s, \-\-server \fR Register server for the provided \s-1UUID,\s0 every new connection to this server will be added the bridge interface .SH "AUTHOR" .IX Header "AUTHOR" Alexander Orlenko . .SH "SEE ALSO" .IX Header "SEE ALSO" \&\fIbt\-adapter\fR\|(1) \fIbt\-agent\fR\|(1) \fIbt\-device\fR\|(1) bluez-tools-2.0~20170911.0.7cb788c/src/bt-network.c000066400000000000000000000215041315563672100211410ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010-2011 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include #include "lib/dbus-common.h" #include "lib/helpers.h" #include "lib/bluez-api.h" static GMainLoop *mainloop = NULL; static void sigterm_handler(int sig) { g_message("%s received", sig == SIGTERM ? "SIGTERM" : "SIGINT"); g_main_loop_quit(mainloop); } static void trap_signals() { /* Add SIGTERM && SIGINT handlers */ struct sigaction sa; memset(&sa, 0, sizeof(sa)); sa.sa_handler = sigterm_handler; sigaction(SIGTERM, &sa, NULL); sigaction(SIGINT, &sa, NULL); } static void _bt_network_property_changed(GDBusConnection *connection, const gchar *sender_name, const gchar *object_path, const gchar *interface_name, const gchar *signal_name, GVariant *parameters, gpointer user_data) { g_assert(user_data != NULL); GMainLoop *mainloop = user_data; GVariant *changed_properties = g_variant_get_child_value(parameters, 1); g_variant_lookup_value(changed_properties, "UUID", NULL); if (g_variant_lookup_value(changed_properties, "Connected", NULL)) { if (g_variant_get_boolean(g_variant_lookup_value(changed_properties, "Connected", NULL)) == TRUE) { g_print("Network service is connected\n"); } else { g_print("Network service is disconnected\n"); g_main_loop_quit(mainloop); } } else if (g_variant_lookup_value(changed_properties, "Interface", NULL)) { g_print("Interface: %s\n", g_variant_get_string(g_variant_lookup_value(changed_properties, "Interface", NULL), NULL)); } else if (g_variant_lookup_value(changed_properties, "UUID", NULL)) { g_print("UUID: %s (%s)\n", uuid2name(g_variant_get_string(g_variant_lookup_value(changed_properties, "UUID", NULL), NULL)), g_variant_get_string(g_variant_lookup_value(changed_properties, "UUID", NULL), NULL)); } } static gchar *adapter_arg = NULL; static gboolean connect_arg = FALSE; static gchar *connect_device_arg = NULL; static gchar *connect_uuid_arg = NULL; static gboolean server_arg = FALSE; static gchar *server_uuid_arg = NULL; static gchar *server_brige_arg = NULL; static gboolean daemon_arg = FALSE; static GOptionEntry entries[] = { {"adapter", 'a', 0, G_OPTION_ARG_STRING, &adapter_arg, "Adapter Name or MAC", ""}, {"connect", 'c', 0, G_OPTION_ARG_NONE, &connect_arg, "Connect to the network device", NULL}, {"server", 's', 0, G_OPTION_ARG_NONE, &server_arg, "Start GN/PANU/NAP server", NULL}, {"daemon", 'd', 0, G_OPTION_ARG_NONE, &daemon_arg, "Run in background (as daemon)"}, {NULL} }; int main(int argc, char *argv[]) { GError *error = NULL; GOptionContext *context; /* Query current locale */ setlocale(LC_CTYPE, ""); dbus_init(); context = g_option_context_new("- a bluetooth network manager"); g_option_context_add_main_entries(context, entries, NULL); g_option_context_set_summary(context, "Version "PACKAGE_VERSION); g_option_context_set_description(context, "Connect Options:\n" " -c, --connect \n" " Where\n" " `name|mac` is a device Name or MAC\n" " `uuid` is:\n" " Profile short name: gn, panu or nap\n\n" "Server Options:\n" " -s, --server \n" " Every new connection to this server will be added the `bridge` interface\n\n" "Report bugs to <"PACKAGE_BUGREPORT">." "Project home page <"PACKAGE_URL">." ); if (!g_option_context_parse(context, &argc, &argv, &error)) { g_print("%s: %s\n", g_get_prgname(), error->message); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } else if (!connect_arg && !server_arg) { g_print("%s", g_option_context_get_help(context, FALSE, NULL)); exit(EXIT_FAILURE); } else if (connect_arg && (argc != 3 || strlen(argv[1]) == 0 || strlen(argv[2]) == 0)) { g_print("%s: Invalid arguments for --connect\n", g_get_prgname()); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } else if (server_arg && (argc != 3 || strlen(argv[1]) == 0 || strlen(argv[2]) == 0)) { g_print("%s: Invalid arguments for --server\n", g_get_prgname()); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } g_option_context_free(context); if (!dbus_system_connect(&error)) { g_printerr("Couldn't connect to DBus system bus: %s\n", error->message); exit(EXIT_FAILURE); } /* Check, that bluetooth daemon is running */ if (!intf_supported(BLUEZ_DBUS_SERVICE_NAME, MANAGER_DBUS_PATH, MANAGER_DBUS_INTERFACE)) { g_printerr("%s: bluez service is not found\n", g_get_prgname()); g_printerr("Did you forget to run bluetoothd?\n"); exit(EXIT_FAILURE); } Adapter *adapter = find_adapter(adapter_arg, &error); exit_if_error(error); if (connect_arg) { connect_device_arg = argv[1]; connect_uuid_arg = argv[2]; Device *device = find_device(adapter, connect_device_arg, &error); exit_if_error(error); if (!intf_supported(BLUEZ_DBUS_SERVICE_NAME, device_get_dbus_object_path(device), NETWORK_DBUS_INTERFACE)) { g_printerr("Network service is not supported by this device\n"); exit(EXIT_FAILURE); } mainloop = g_main_loop_new(NULL, FALSE); Network *network = network_new(device_get_dbus_object_path(device)); guint prop_sig_sub_id = g_dbus_connection_signal_subscribe(system_conn, "org.bluez", "org.freedesktop.DBus.Properties", "PropertiesChanged", network_get_dbus_object_path(network), NULL, G_DBUS_SIGNAL_FLAGS_NONE, _bt_network_property_changed, mainloop, NULL); if (network_get_connected(network, NULL) == TRUE) { g_print("Network service is already connected\n"); } else { gchar *intf = (gchar *) network_connect(network, connect_uuid_arg, &error); exit_if_error(error); trap_signals(); g_main_loop_run(mainloop); /* Force disconnect the network device */ if (network_get_connected(network, NULL) == TRUE) { network_disconnect(network, NULL); } g_free(intf); } g_dbus_connection_signal_unsubscribe(system_conn, prop_sig_sub_id); g_main_loop_unref(mainloop); g_object_unref(network); g_object_unref(device); } else if (server_arg) { server_uuid_arg = argv[1]; server_brige_arg = argv[2]; if (g_ascii_strcasecmp(server_uuid_arg, "gn") != 0 && g_ascii_strcasecmp(server_uuid_arg, "panu") != 0 && g_ascii_strcasecmp(server_uuid_arg, "nap") != 0) { g_print("%s: Invalid server UUID: %s\n", g_get_prgname(), server_uuid_arg); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } if (!intf_supported(BLUEZ_DBUS_SERVICE_NAME, adapter_get_dbus_object_path(adapter), NETWORK_SERVER_DBUS_INTERFACE)) { g_printerr("Network server is not supported by this adapter\n"); exit(EXIT_FAILURE); } gchar *server_uuid_upper = g_ascii_strup(server_uuid_arg, -1); NetworkServer *network_server = network_server_new(adapter_get_dbus_object_path(adapter)); network_server_register(network_server, server_uuid_arg, server_brige_arg, &error); exit_if_error(error); g_print("%s server registered\n", server_uuid_upper); mainloop = g_main_loop_new(NULL, FALSE); if (daemon_arg) { pid_t pid, sid; /* Fork off the parent process */ pid = fork(); if (pid < 0) exit(EXIT_FAILURE); /* Ok, terminate parent proccess */ if (pid > 0) exit(EXIT_SUCCESS); /* Create a new SID for the child process */ sid = setsid(); if (sid < 0) exit(EXIT_FAILURE); /* Close out the standard file descriptors */ close(STDIN_FILENO); close(STDOUT_FILENO); close(STDERR_FILENO); } trap_signals(); g_main_loop_run(mainloop); network_server_unregister(network_server, server_uuid_arg, &error); exit_if_error(error); g_print("%s server unregistered\n", server_uuid_upper); g_main_loop_unref(mainloop); g_free(server_uuid_upper); g_object_unref(network_server); } g_object_unref(adapter); dbus_disconnect(); exit(EXIT_SUCCESS); } bluez-tools-2.0~20170911.0.7cb788c/src/bt-obex.1000066400000000000000000000141601315563672100203230ustar00rootroot00000000000000.\" Automatically generated by Pod::Man 2.27 (Pod::Simple 3.28) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is turned on, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{ . if \nF \{ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" .\" Accent mark definitions (@(#)ms.acc 1.5 88/02/08 SMI; from UCB 4.2). .\" Fear. Run. Save yourself. No user-serviceable parts. . \" fudge factors for nroff and troff .if n \{\ . ds #H 0 . ds #V .8m . ds #F .3m . ds #[ \f1 . ds #] \fP .\} .if t \{\ . ds #H ((1u-(\\\\n(.fu%2u))*.13m) . ds #V .6m . ds #F 0 . ds #[ \& . ds #] \& .\} . \" simple accents for nroff and troff .if n \{\ . ds ' \& . ds ` \& . ds ^ \& . ds , \& . ds ~ ~ . ds / .\} .if t \{\ . ds ' \\k:\h'-(\\n(.wu*8/10-\*(#H)'\'\h"|\\n:u" . ds ` \\k:\h'-(\\n(.wu*8/10-\*(#H)'\`\h'|\\n:u' . ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'^\h'|\\n:u' . ds , \\k:\h'-(\\n(.wu*8/10)',\h'|\\n:u' . ds ~ \\k:\h'-(\\n(.wu-\*(#H-.1m)'~\h'|\\n:u' . ds / \\k:\h'-(\\n(.wu*8/10-\*(#H)'\z\(sl\h'|\\n:u' .\} . \" troff and (daisy-wheel) nroff accents .ds : \\k:\h'-(\\n(.wu*8/10-\*(#H+.1m+\*(#F)'\v'-\*(#V'\z.\h'.2m+\*(#F'.\h'|\\n:u'\v'\*(#V' .ds 8 \h'\*(#H'\(*b\h'-\*(#H' .ds o \\k:\h'-(\\n(.wu+\w'\(de'u-\*(#H)/2u'\v'-.3n'\*(#[\z\(de\v'.3n'\h'|\\n:u'\*(#] .ds d- \h'\*(#H'\(pd\h'-\w'~'u'\v'-.25m'\f2\(hy\fP\v'.25m'\h'-\*(#H' .ds D- D\\k:\h'-\w'D'u'\v'-.11m'\z\(hy\v'.11m'\h'|\\n:u' .ds th \*(#[\v'.3m'\s+1I\s-1\v'-.3m'\h'-(\w'I'u*2/3)'\s-1o\s+1\*(#] .ds Th \*(#[\s+2I\s-2\h'-\w'I'u*3/5'\v'-.3m'o\v'.3m'\*(#] .ds ae a\h'-(\w'a'u*4/10)'e .ds Ae A\h'-(\w'A'u*4/10)'E . \" corrections for vroff .if v .ds ~ \\k:\h'-(\\n(.wu*9/10-\*(#H)'\s-2\u~\d\s+2\h'|\\n:u' .if v .ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'\v'-.4m'^\v'.4m'\h'|\\n:u' . \" for low resolution devices (crt and lpr) .if \n(.H>23 .if \n(.V>19 \ \{\ . ds : e . ds 8 ss . ds o a . ds d- d\h'-1'\(ga . ds D- D\h'-1'\(hy . ds th \o'bp' . ds Th \o'LP' . ds ae ae . ds Ae AE .\} .rm #[ #] #H #V #F C .\" ======================================================================== .\" .IX Title "bt-obex 1" .TH bt-obex 1 "2014-08-01" "" "bluez-tools" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" bt\-obex \- a bluetooth OBEX client/server .SH "SYNOPSIS" .IX Header "SYNOPSIS" bt-obex [\s-1OPTION...\s0] .PP Help Options: \-h, \-\-help .PP Application Options: \-a, \-\-adapter= \-s, \-\-server [] \-p, \-\-opp \-f, \-\-ftp= .SH "DESCRIPTION" .IX Header "DESCRIPTION" This utility implemented support of Object Push Profile (\s-1OPP\s0) and File Transfer Profile (\s-1FTP\s0). You can send and receive files to/from remote device using this tool. .SH "OPTIONS" .IX Header "OPTIONS" \&\fB\-h, \-\-help\fR Show help .PP \&\fB\-a, \-\-adapter \fR Specify adapter to use by his Name or \s-1MAC\s0 address (if this option does not defined \- default adapter used) .PP \&\fB\-s, \-\-server []\fR Register agent at \s-1OBEX\s0 server and set incoming/root directory to `path` or current folder will be used; Agent is used to accept/reject incoming bluetooth object push requests .PP \&\fB\-p, \-\-opp \fR Send local file to the specified remote device using object push profile .PP \&\fB\-f, \-\-ftp \fR Start \s-1FTP\s0 session with remote device; If session opened successfuly, \s-1FTP\s0 shell will be opened .PP .Vb 1 \& FTP commands: \& \& help Show help message \& exit Close FTP session \& cd Change the current folder of the remote device \& mkdir Create a new folder in the remote device \& ls List folder contents \& get Copy the src file (from remote device) to the dst file (on local filesystem) \& put Copy the src file (from local filesystem) to the dst file (on remote device) \& cp Copy a file within the remote device from src file to dst file \& mv Move a file within the remote device from src file to dst file \& rm Deletes the specified file/folder .Ve .SH "AUTHOR" .IX Header "AUTHOR" Alexander Orlenko . .SH "SEE ALSO" .IX Header "SEE ALSO" \&\fIbt\-adapter\fR\|(1) \fIbt\-agent\fR\|(1) \fIbt\-device\fR\|(1) \fIbt\-network\fR\|(1) bluez-tools-2.0~20170911.0.7cb788c/src/bt-obex.c000066400000000000000000001133171315563672100204110ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include #include #include #include "lib/dbus-common.h" #include "lib/helpers.h" #include "lib/bluez-api.h" static GHashTable *_transfers = NULL; static GHashTable *_transfer_infos = NULL; static GMainLoop *mainloop = NULL; static gchar *_root_path = NULL; static gboolean _update_progress = FALSE; typedef struct _ObexTransferInfo ObexTransferInfo; struct _ObexTransferInfo { gchar *filename; guint64 filesize; gchar *obex_root; gchar *status; }; static void sigterm_handler(int sig) { g_message("%s received", sig == SIGTERM ? "SIGTERM" : "SIGINT"); if (g_main_loop_is_running(mainloop)) g_main_loop_quit(mainloop); } static void _obex_server_object_manager_handler(GDBusConnection *connection, const gchar *sender_name, const gchar *object_path, const gchar *interface_name, const gchar *signal_name, GVariant *parameters, gpointer user_data) { if(g_strcmp0(signal_name, "InterfacesAdded") == 0) { const gchar *interface_object_path = g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL); GVariant *interfaces_and_properties = g_variant_get_child_value(parameters, 1); GVariant *properties = NULL; if(g_variant_lookup(interfaces_and_properties, OBEX_TRANSFER_DBUS_INTERFACE, "@a{sv}", &properties)) { g_print("[OBEX Server] Transfer started\n"); ObexTransfer *t = obex_transfer_new(interface_object_path); g_hash_table_insert(_transfers, g_strdup(interface_object_path), t); ObexTransferInfo *info = g_malloc0(sizeof(ObexTransferInfo)); info->filesize = g_variant_get_uint64(g_variant_lookup_value(properties, "Size", NULL)); info->status = g_strdup(g_variant_get_string(g_variant_lookup_value(properties, "Status", NULL), NULL)); ObexSession *session = obex_session_new(g_variant_get_string(g_variant_lookup_value(properties, "Session", NULL), NULL)); info->obex_root = g_strdup(obex_session_get_root(session, NULL)); g_object_unref(session); g_hash_table_insert(_transfer_infos, g_strdup(interface_object_path), info); } if(g_variant_lookup(interfaces_and_properties, OBEX_SESSION_DBUS_INTERFACE, "@a{sv}", &properties)) { g_print("[OBEX Server] OBEX session opened\n"); } g_variant_unref(interfaces_and_properties); if(properties) g_variant_unref(properties); } else if(g_strcmp0(signal_name, "InterfacesRemoved") == 0) { const gchar *interface_object_path = g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL); GVariant *interfaces = g_variant_get_child_value(parameters, 1); const gchar **inf_array = g_variant_get_strv(interfaces, NULL); g_variant_unref(interfaces); const gchar **inf = NULL; for(inf = inf_array; *inf != NULL; inf++) { if(g_strcmp0(*inf, OBEX_TRANSFER_DBUS_INTERFACE) == 0) { g_print("[OBEX Server] OBEX transfer closed\n"); ObexTransfer *transfer = g_hash_table_lookup(_transfers, interface_object_path); g_hash_table_remove(_transfers, interface_object_path); g_object_unref(transfer); g_free(g_hash_table_lookup(_transfer_infos, interface_object_path)); g_hash_table_remove(_transfer_infos, interface_object_path); } if(g_strcmp0(*inf, OBEX_SESSION_DBUS_INTERFACE) == 0) { g_print("[OBEX Server] OBEX session closed\n"); } } g_free(inf_array); } } static void _obex_server_properties_handler(GDBusConnection *connection, const gchar *sender_name, const gchar *object_path, const gchar *interface_name, const gchar *signal_name, GVariant *parameters, gpointer user_data) { const gchar *arg0 = g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL); GVariant *changed_properties = g_variant_get_child_value(parameters, 1); if(g_strcmp0(arg0, OBEX_TRANSFER_DBUS_INTERFACE) == 0) { ObexTransfer *transfer = g_hash_table_lookup(_transfers, object_path); guint64 size = 0x0; guint64 transferred = 0x0; obex_transfer_get_size(transfer, NULL); g_variant_lookup(changed_properties, "Size", "t", &size); if(!size) size = obex_transfer_get_size(transfer, NULL); g_variant_lookup(changed_properties, "Transferred", "t", &transferred); if(size && transferred) { guint pp = (transferred / (gfloat) size)*100; if (!_update_progress) { g_print("[OBEXTransfer] Progress: %3u%%", pp); _update_progress = TRUE; } else { g_print("\b\b\b\b%3u%%", pp); } if (pp == 100) { g_print("\n"); _update_progress = FALSE; } } gchar *status = NULL; g_variant_lookup(changed_properties, "Status", "s", &status); if(status) { if(g_strcmp0(status, "active") == 0) { // g_print("[OBEX Server] Transfer active\n"); } else if(g_strcmp0(status, "complete") == 0) { g_print("[OBEX Server] Transfer succeeded\n"); ObexTransferInfo *info = g_hash_table_lookup(_transfer_infos, object_path); g_rename(g_build_filename(info->obex_root, info->filename, NULL), g_build_filename(_root_path, info->filename, NULL)); } else if(g_strcmp0(status, "error") == 0) { g_print("[OBEX Server] Transfer failed\n"); } else if(g_strcmp0(status, "queued") == 0) { g_print("[OBEX Server] Transfer queued\n"); } else if(g_strcmp0(status, "suspended") == 0) { g_print("[OBEX Server] Transfer halted\n"); } g_free(status); } } g_variant_unref(changed_properties); } static void _obex_opp_client_object_manager_handler(GDBusConnection *connection, const gchar *sender_name, const gchar *object_path, const gchar *interface_name, const gchar *signal_name, GVariant *parameters, gpointer user_data) { if(g_strcmp0(signal_name, "InterfacesAdded") == 0) { const gchar *interface_object_path = g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL); GVariant *interfaces_and_properties = g_variant_get_child_value(parameters, 1); GVariant *properties = NULL; if(g_variant_lookup(interfaces_and_properties, OBEX_TRANSFER_DBUS_INTERFACE, "@a{sv}", &properties)) { // g_print("[OBEX Client] Transfer started\n"); ObexTransfer *t = obex_transfer_new(interface_object_path); g_hash_table_insert(_transfers, g_strdup(interface_object_path), t); ObexTransferInfo *info = g_malloc0(sizeof(ObexTransferInfo)); info->filesize = g_variant_get_uint64(g_variant_lookup_value(properties, "Size", NULL)); info->filename = g_strdup(g_variant_get_string(g_variant_lookup_value(properties, "Name", NULL), NULL)); info->status = g_strdup(g_variant_get_string(g_variant_lookup_value(properties, "Status", NULL), NULL)); ObexSession *session = obex_session_new(g_variant_get_string(g_variant_lookup_value(properties, "Session", NULL), NULL)); info->obex_root = g_strdup(obex_session_get_root(session, NULL)); g_object_unref(session); g_hash_table_insert(_transfer_infos, g_strdup(interface_object_path), info); if(g_strcmp0(info->status, "queued") == 0) g_print("[Transfer#%s] Waiting...\n", info->filename); } if(g_variant_lookup(interfaces_and_properties, OBEX_SESSION_DBUS_INTERFACE, "@a{sv}", &properties)) { // g_print("[OBEX Client] OBEX session opened\n"); } g_variant_unref(interfaces_and_properties); if(properties) g_variant_unref(properties); } else if(g_strcmp0(signal_name, "InterfacesRemoved") == 0) { const gchar *interface_object_path = g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL); GVariant *interfaces = g_variant_get_child_value(parameters, 1); const gchar **inf_array = g_variant_get_strv(interfaces, NULL); g_variant_unref(interfaces); const gchar **inf = NULL; for(inf = inf_array; *inf != NULL; inf++) { if(g_strcmp0(*inf, OBEX_TRANSFER_DBUS_INTERFACE) == 0) { // g_print("[OBEX Client] OBEX transfer closed\n"); ObexTransfer *transfer = g_hash_table_lookup(_transfers, interface_object_path); g_hash_table_remove(_transfers, interface_object_path); g_object_unref(transfer); g_free(g_hash_table_lookup(_transfer_infos, interface_object_path)); g_hash_table_remove(_transfer_infos, interface_object_path); if (g_main_loop_is_running(mainloop)) g_main_loop_quit(mainloop); } if(g_strcmp0(*inf, OBEX_SESSION_DBUS_INTERFACE) == 0) { // g_print("[OBEX Client] OBEX session closed\n"); } } g_free(inf_array); } } static void _obex_opp_client_properties_handler(GDBusConnection *connection, const gchar *sender_name, const gchar *object_path, const gchar *interface_name, const gchar *signal_name, GVariant *parameters, gpointer user_data) { const gchar *arg0 = g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL); GVariant *changed_properties = g_variant_get_child_value(parameters, 1); if(g_strcmp0(arg0, OBEX_TRANSFER_DBUS_INTERFACE) == 0) { ObexTransfer *transfer = g_hash_table_lookup(_transfers, object_path); ObexTransferInfo *info = g_hash_table_lookup(_transfer_infos, object_path); guint64 size = 0x0; guint64 transferred = 0x0; obex_transfer_get_size(transfer, NULL); g_variant_lookup(changed_properties, "Size", "t", &size); if(!size) size = obex_transfer_get_size(transfer, NULL); g_variant_lookup(changed_properties, "Transferred", "t", &transferred); if(size && transferred && g_strcmp0(info->status, "active") == 0) { guint pp = (transferred / (gfloat) size)*100; if (!_update_progress) { g_print("[Transfer#%s] Progress: %3u%%", obex_transfer_get_name(transfer, NULL), pp); _update_progress = TRUE; } else { g_print("\b\b\b\b%3u%%", pp); } if (pp == 100) { g_print("\n"); _update_progress = FALSE; } } gchar *status = NULL; g_variant_lookup(changed_properties, "Status", "s", &status); if(status) { g_free(info->status); info->status = g_strdup(status); if(g_strcmp0(status, "active") == 0) { // g_print("[Client Server] Transfer active\n"); } else if(g_strcmp0(status, "complete") == 0) { if(_update_progress) { _update_progress = FALSE; g_print("\b\b\b\b%3u%%", 100); g_print("\n"); } g_print("[Transfer#%s] Completed\n", info->filename); } else if(g_strcmp0(status, "error") == 0) { if(_update_progress) { _update_progress = FALSE; g_print("\n"); } g_print("[Transfer#%s] Failed\n", info->filename); } else if(g_strcmp0(status, "queued") == 0) { // g_print("[OBEX Client] Transfer queued\n"); } else if(g_strcmp0(status, "suspended") == 0) { if(_update_progress) { _update_progress = FALSE; g_print("\n"); } g_print("[Transfer#%s] Suspended\n", info->filename); } g_free(status); } } g_variant_unref(changed_properties); } void _agent_approved_callback(ObexAgent *obex_agent, const gchar* obex_transfer_path, const gchar *name, const guint64 size, gpointer user_data) { ObexTransferInfo *info = g_hash_table_lookup(_transfer_infos, obex_transfer_path); if(!info) { info = g_malloc0(sizeof(ObexTransferInfo)); g_hash_table_insert(_transfer_infos, g_strdup(obex_transfer_path), info); ObexTransfer *transfer = g_hash_table_lookup(_transfers, obex_transfer_path); ObexSession *session = obex_session_new(obex_transfer_get_session(transfer, NULL)); info->obex_root = g_strdup(obex_session_get_root(session, NULL)); } info->filename = g_strdup(name); info->filesize = size; } /* Main arguments */ static gchar *adapter_arg = NULL; static gboolean server_arg = FALSE; static gboolean auto_accept = FALSE; static gchar *server_path_arg = NULL; static gboolean opp_arg = FALSE; static gchar *opp_device_arg = NULL; static gchar *opp_file_arg = NULL; static gchar *ftp_arg = NULL; static GOptionEntry entries[] = { {"adapter", 'a', 0, G_OPTION_ARG_STRING, &adapter_arg, "Adapter name or MAC", ""}, {"server", 's', 0, G_OPTION_ARG_NONE, &server_arg, "Register self as OBEX server", NULL}, {"auto-accept", 'y', 0, G_OPTION_ARG_NONE, &auto_accept, "Automatically accept incoming files", NULL}, {"opp", 'p', 0, G_OPTION_ARG_NONE, &opp_arg, "Send file to remote device", NULL}, {"ftp", 'f', 0, G_OPTION_ARG_STRING, &ftp_arg, "Start FTP session with remote device", ""}, {NULL} }; int main(int argc, char *argv[]) { GError *error = NULL; GOptionContext *context; /* Query current locale */ setlocale(LC_CTYPE, ""); dbus_init(); context = g_option_context_new(" - a bluetooth OBEX client/server"); g_option_context_add_main_entries(context, entries, NULL); g_option_context_set_summary(context, "Version "PACKAGE_VERSION); g_option_context_set_description(context, "Server Options:\n" " -s, --server []\n" " Register self at OBEX server and use given `path` as OPP save directory\n" " If `path` does not specified - use current directory\n\n" "OPP Options:\n" " -p, --opp \n" " Send `file` to remote device using Object Push Profile\n\n" "Report bugs to <"PACKAGE_BUGREPORT">." "Project home page <"PACKAGE_URL">." ); if (!g_option_context_parse(context, &argc, &argv, &error)) { g_print("%s: %s\n", g_get_prgname(), error->message); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } else if (!server_arg && !opp_arg && (!ftp_arg || strlen(ftp_arg) == 0)) { g_print("%s", g_option_context_get_help(context, FALSE, NULL)); exit(EXIT_FAILURE); } else if (server_arg && argc != 1 && (argc != 2 || strlen(argv[1]) == 0)) { g_print("%s: Invalid arguments for --server\n", g_get_prgname()); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } else if (opp_arg && (argc != 3 || strlen(argv[1]) == 0 || strlen(argv[2]) == 0)) { g_print("%s: Invalid arguments for --opp\n", g_get_prgname()); g_print("Try `%s --help` for more information.\n", g_get_prgname()); exit(EXIT_FAILURE); } g_option_context_free(context); if (!dbus_system_connect(&error)) { g_printerr("Couldn't connect to DBus system bus: %s\n", error->message); exit(EXIT_FAILURE); } if (!dbus_session_connect(&error)) { g_printerr("Couldn't connect to DBus session bus: %s\n", error->message); exit(EXIT_FAILURE); } /* Check, that bluetooth daemon is running */ if (!intf_supported(BLUEZ_DBUS_SERVICE_NAME, MANAGER_DBUS_PATH, MANAGER_DBUS_INTERFACE)) { g_printerr("%s: bluez service is not found\n", g_get_prgname()); g_printerr("Did you forget to run bluetoothd?\n"); exit(EXIT_FAILURE); } /* Check, that obexd daemon is running */ if (!intf_supported(BLUEZ_OBEX_DBUS_SERVICE_NAME, MANAGER_DBUS_PATH, MANAGER_DBUS_INTERFACE)) { g_printerr("%s: obex service is not found\n", g_get_prgname()); g_printerr("Did you forget to run obexd?\n"); exit(EXIT_FAILURE); } if (server_arg) { if (argc == 2) { server_path_arg = argv[1]; } /* Check that `path` is valid */ gchar *root_folder = server_path_arg == NULL ? g_get_current_dir() : g_strdup(server_path_arg); if (!is_dir(root_folder, &error)) { exit_if_error(error); } if(!write_access(root_folder, &error)) { exit_if_error(error); } _transfers = g_hash_table_new(g_str_hash, g_str_equal); _transfer_infos = g_hash_table_new(g_str_hash, g_str_equal); ObexAgentManager *manager = obex_agent_manager_new(); guint obex_server_object_id = g_dbus_connection_signal_subscribe(session_conn, "org.bluez.obex", "org.freedesktop.DBus.ObjectManager", NULL, NULL, NULL, G_DBUS_SIGNAL_FLAGS_NONE, _obex_server_object_manager_handler, NULL, NULL); guint obex_server_properties_id = g_dbus_connection_signal_subscribe(session_conn, "org.bluez.obex", "org.freedesktop.DBus.Properties", "PropertiesChanged", NULL, NULL, G_DBUS_SIGNAL_FLAGS_NONE, _obex_server_properties_handler, NULL, NULL); ObexAgent *agent = obex_agent_new(root_folder, auto_accept); _root_path = g_strdup(root_folder); g_free(root_folder); obex_agent_set_approved_callback(agent, _agent_approved_callback, NULL); obex_agent_manager_register_agent(manager, OBEX_AGENT_DBUS_PATH, &error); exit_if_error(error); mainloop = g_main_loop_new(NULL, FALSE); /* Add SIGTERM && SIGINT handlers */ struct sigaction sa; memset(&sa, 0, sizeof (sa)); sa.sa_handler = sigterm_handler; sigaction(SIGTERM, &sa, NULL); sigaction(SIGINT, &sa, NULL); g_main_loop_run(mainloop); /* Waiting for connections... */ g_main_loop_unref(mainloop); /* Stop active transfers */ GHashTableIter iter; gpointer key, value; g_hash_table_iter_init(&iter, _transfers); while (g_hash_table_iter_next(&iter, &key, &value)) { ObexTransfer *t = OBEX_TRANSFER(value); obex_transfer_cancel(t, NULL); // skip errors g_object_unref(t); g_hash_table_iter_remove(&iter); } g_hash_table_unref(_transfers); // Remove transfer information g_hash_table_iter_init(&iter, _transfer_infos); while (g_hash_table_iter_next(&iter, &key, &value)) { g_free(value); g_hash_table_iter_remove(&iter); } g_hash_table_unref(_transfers); g_dbus_connection_signal_unsubscribe(session_conn, obex_server_object_id); g_dbus_connection_signal_unsubscribe(session_conn, obex_server_properties_id); g_free(_root_path); obex_agent_manager_unregister_agent(manager, OBEX_AGENT_DBUS_PATH, &error); g_object_unref(agent); g_object_unref(manager); } else if (opp_arg) { opp_device_arg = argv[1]; opp_file_arg = argv[2]; /* Check that `file` is valid */ if (!is_file(opp_file_arg, &error)) { exit_if_error(error); } _transfers = g_hash_table_new(g_str_hash, g_str_equal); _transfer_infos = g_hash_table_new(g_str_hash, g_str_equal); gchar * files_to_send[] = {NULL, NULL}; files_to_send[0] = g_path_is_absolute(opp_file_arg) ? g_strdup(opp_file_arg) : get_absolute_path(opp_file_arg); /* Get source address (address of adapter) */ Adapter *adapter = find_adapter(adapter_arg, &error); exit_if_error(error); gchar *src_address = g_strdup(adapter_get_address(adapter, &error)); exit_if_error(error); /* Get destination address (address of remote device) */ gchar *dst_address = NULL; if (g_regex_match_simple("^\\x{2}:\\x{2}:\\x{2}:\\x{2}:\\x{2}:\\x{2}$", opp_device_arg, 0, 0)) { dst_address = g_strdup(opp_device_arg); } else { Device *device = find_device(adapter, opp_device_arg, &error); exit_if_error(error); dst_address = g_strdup(device_get_address(device, &error)); exit_if_error(error); g_object_unref(device); } g_object_unref(adapter); /* Build arguments */ GVariantBuilder *b = g_variant_builder_new(G_VARIANT_TYPE_VARDICT); g_variant_builder_add(b, "{sv}", "Target", g_variant_new_string("opp")); g_variant_builder_add(b, "{sv}", "Source", g_variant_new_string(src_address)); GVariant *device_dict = g_variant_builder_end(b); g_variant_builder_unref(b); mainloop = g_main_loop_new(NULL, FALSE); ObexClient *client = obex_client_new(); const gchar *session_path = obex_client_create_session(client, dst_address, device_dict, &error); exit_if_error(error); ObexSession *session = obex_session_new(session_path); ObexObjectPush *oop = obex_object_push_new(obex_session_get_dbus_object_path(session)); // initialize GDBus OBEX OPP client callbacks guint obex_opp_object_man_id = g_dbus_connection_signal_subscribe(session_conn, "org.bluez.obex", "org.freedesktop.DBus.ObjectManager", NULL, NULL, NULL, G_DBUS_SIGNAL_FLAGS_NONE, _obex_opp_client_object_manager_handler, NULL, NULL); guint obex_opp_properties_id = g_dbus_connection_signal_subscribe(session_conn, "org.bluez.obex", "org.freedesktop.DBus.Properties", "PropertiesChanged", NULL, NULL, G_DBUS_SIGNAL_FLAGS_NONE, _obex_opp_client_properties_handler, NULL, NULL); /* Sending file(s) */ obex_object_push_send_file(oop, files_to_send[0], &error); exit_if_error(error); /* Add SIGTERM && SIGINT handlers */ struct sigaction sa; memset(&sa, 0, sizeof (sa)); sa.sa_handler = sigterm_handler; sigaction(SIGTERM, &sa, NULL); sigaction(SIGINT, &sa, NULL); g_main_loop_run(mainloop); /* Sending files process here ?? */ g_main_loop_unref(mainloop); g_dbus_connection_signal_unsubscribe(session_conn, obex_opp_object_man_id); g_dbus_connection_signal_unsubscribe(session_conn, obex_opp_properties_id); /* Stop active transfers */ GHashTableIter iter; gpointer key, value; g_hash_table_iter_init(&iter, _transfers); while (g_hash_table_iter_next(&iter, &key, &value)) { ObexTransfer *t = OBEX_TRANSFER(value); obex_transfer_cancel(t, NULL); // skip errors g_object_unref(t); g_hash_table_iter_remove(&iter); } g_hash_table_unref(_transfers); // Remove transfer information objects g_hash_table_iter_init(&iter, _transfer_infos); while (g_hash_table_iter_next(&iter, &key, &value)) { g_free(value); g_hash_table_iter_remove(&iter); } g_hash_table_unref(_transfers); g_object_unref(client); g_variant_unref(device_dict); g_free(src_address); g_free(dst_address); g_free(files_to_send[0]); files_to_send[0] = NULL; } else if (ftp_arg) { /* Get source address (address of adapter) */ Adapter *adapter = find_adapter(adapter_arg, &error); exit_if_error(error); gchar *src_address = g_strdup(adapter_get_address(adapter, &error)); exit_if_error(error); /* Get destination address (address of remote device) */ Device *device = find_device(adapter, ftp_arg, &error); exit_if_error(error); gchar *dst_address = g_strdup(device == NULL ? ftp_arg : device_get_address(device, &error)); exit_if_error(error); g_object_unref(device); g_object_unref(adapter); /* Build arguments */ GVariantBuilder *b; GVariant *device_dict; b = g_variant_builder_new(G_VARIANT_TYPE("a{sv}")); g_variant_builder_add(b, "{sv}", "Target", g_variant_new_string("ftp")); g_variant_builder_add(b, "{sv}", "Source", g_variant_new_string(src_address)); device_dict = g_variant_builder_end(b); g_variant_builder_unref(b); ObexClient *client = g_object_new(OBEX_CLIENT_TYPE, NULL); ObexAgent *agent = g_object_new(OBEX_AGENT_TYPE, NULL); /* Create FTP session */ gchar *session_path = g_strdup(obex_client_create_session(client, dst_address, device_dict, &error)); exit_if_error(error); ObexFileTransfer *ftp_session = obex_file_transfer_new(session_path); g_free(session_path); g_print("FTP session opened\n"); while (TRUE) { gchar *cmd = readline("> "); if (cmd == NULL) { continue; } else { add_history(cmd); } gint f_argc; gchar **f_argv; /* Parsing command line */ if (!g_shell_parse_argv(cmd, &f_argc, &f_argv, &error)) { g_print("%s\n", error->message); g_error_free(error); error = NULL; g_free(cmd); continue; } /* Execute commands */ if (g_strcmp0(f_argv[0], "cd") == 0) { if (f_argc != 2 || strlen(f_argv[1]) == 0) { g_print("invalid arguments\n"); } else { obex_file_transfer_change_folder(ftp_session, f_argv[1], &error); if (error) { g_print("%s\n", error->message); g_error_free(error); error = NULL; } } } else if (g_strcmp0(f_argv[0], "mkdir") == 0) { if (f_argc != 2 || strlen(f_argv[1]) == 0) { g_print("invalid arguments\n"); } else { obex_file_transfer_create_folder(ftp_session, f_argv[1], &error); if (error) { g_print("%s\n", error->message); g_error_free(error); error = NULL; } } } else if (g_strcmp0(f_argv[0], "ls") == 0) { if (f_argc != 1) { g_print("invalid arguments\n"); } else { // GPtrArray *folders = obex_file_transfer_list_folder(ftp_session, &error); GVariant *folder_list = obex_file_transfer_list_folder(ftp_session, &error); GPtrArray *folders = g_ptr_array_new(); gsize arr_size = 0; // Pass the pointer folders->pdata = (gpointer) g_variant_get_fixed_array(folder_list, &arr_size, sizeof(gpointer)); folders->len = arr_size; if (error) { g_print("%s\n", error->message); g_error_free(error); error = NULL; } else { for (int i = 0; i < folders->len; i++) { /* GHashTable *el = g_ptr_array_index(folders, i); g_print( "%s\t%llu\t%s\n", g_value_get_string(g_hash_table_lookup(el, "Type")), G_VALUE_HOLDS_UINT64(g_hash_table_lookup(el, "Size")) ? g_value_get_uint64(g_hash_table_lookup(el, "Size")) : 0, g_value_get_string(g_hash_table_lookup(el, "Name")) ); */ // DO NOT FREE THIS GVariant *el = g_ptr_array_index(folders, i); g_print( "%s\t%" G_GINT64_FORMAT"\t%s\n", g_variant_get_string(g_variant_lookup_value(el, "Type", G_VARIANT_TYPE("s")), NULL), g_variant_get_uint64(g_variant_lookup_value(el, "Size", G_VARIANT_TYPE("t"))), g_variant_get_string(g_variant_lookup_value(el, "Name", G_VARIANT_TYPE("s")), NULL) ); } } // Do not free the contents of the array. g_variant_unref will free contents if (folders) g_ptr_array_free(folders, FALSE); if (folder_list) g_variant_unref(folder_list); /*obexclient_remove_session(client, obexclient_file_transfer_get_dbus_object_path(ftp_session), &error); exit_if_error(error); g_object_unref(ftp_session); session_path = obexclient_create_session(client, device_dict, &error); exit_if_error(error); ftp_session = g_object_new(OBEXCLIENT_FILE_TRANSFER_TYPE, "DBusObjectPath", session_path, NULL); g_free(session_path);*/ } } else if (g_strcmp0(f_argv[0], "get") == 0) { if (f_argc != 3 || strlen(f_argv[1]) == 0 || strlen(f_argv[2]) == 0) { g_print("invalid arguments\n"); } else { gchar *abs_dst_path = get_absolute_path(f_argv[2]); gchar *dir = g_path_get_dirname(abs_dst_path); if (!is_dir(dir, &error)) { g_print("%s\n", error->message); g_error_free(error); error = NULL; } else { obex_file_transfer_get_file(ftp_session, abs_dst_path, f_argv[1], &error); if (error) { g_print("%s\n", error->message); g_error_free(error); error = NULL; } } g_free(dir); g_free(abs_dst_path); } } else if (g_strcmp0(f_argv[0], "put") == 0) { if (f_argc != 3 || strlen(f_argv[1]) == 0 || strlen(f_argv[2]) == 0) { g_print("invalid arguments\n"); } else { gchar *abs_src_path = get_absolute_path(f_argv[1]); if (!is_file(abs_src_path, &error)) { g_print("%s\n", error->message); g_error_free(error); error = NULL; } else { obex_file_transfer_put_file(ftp_session, abs_src_path, f_argv[2], &error); if (error) { g_print("%s\n", error->message); g_error_free(error); error = NULL; } } g_free(abs_src_path); } } else if (g_strcmp0(f_argv[0], "cp") == 0) { if (f_argc != 3 || strlen(f_argv[1]) == 0 || strlen(f_argv[2]) == 0) { g_print("invalid arguments\n"); } else { obex_file_transfer_copy_file(ftp_session, f_argv[1], f_argv[2], &error); if (error) { g_print("%s\n", error->message); g_error_free(error); error = NULL; } } } else if (g_strcmp0(f_argv[0], "mv") == 0) { if (f_argc != 3 || strlen(f_argv[1]) == 0 || strlen(f_argv[2]) == 0) { g_print("invalid arguments\n"); } else { obex_file_transfer_move_file(ftp_session, f_argv[1], f_argv[2], &error); if (error) { g_print("%s\n", error->message); g_error_free(error); error = NULL; } } } else if (g_strcmp0(f_argv[0], "rm") == 0) { if (f_argc != 2 || strlen(f_argv[1]) == 0) { g_print("invalid arguments\n"); } else { obex_file_transfer_delete(ftp_session, f_argv[1], &error); if (error) { g_print("%s\n", error->message); g_error_free(error); error = NULL; } } } else if (g_strcmp0(f_argv[0], "help") == 0) { g_print( "help\t\t\tShow this message\n" "exit\t\t\tClose FTP session\n" "cd \t\tChange the current folder of the remote device\n" "mkdir \t\tCreate a new folder in the remote device\n" "ls\t\t\tList folder contents\n" "get \t\tCopy the src file (from remote device) to the dst file (on local filesystem)\n" "put \t\tCopy the src file (from local filesystem) to the dst file (on remote device)\n" "cp \t\tCopy a file within the remote device from src file to dst file\n" "mv \t\tMove a file within the remote device from src file to dst file\n" "rm \t\tDeletes the specified file/folder\n" ); } else if (g_strcmp0(f_argv[0], "exit") == 0 || g_strcmp0(f_argv[0], "quit") == 0) { obex_client_remove_session(client, obex_file_transfer_get_dbus_object_path(ftp_session), &error); exit_if_error(error); g_strfreev(f_argv); g_free(cmd); break; } else { g_print("invalid command\n"); } g_strfreev(f_argv); g_free(cmd); } g_object_unref(agent); g_object_unref(client); g_object_unref(ftp_session); g_variant_unref(device_dict); g_free(src_address); g_free(dst_address); } dbus_disconnect(); exit(EXIT_SUCCESS); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/000077500000000000000000000000001315563672100174455ustar00rootroot00000000000000bluez-tools-2.0~20170911.0.7cb788c/src/lib/agent-helper.c000066400000000000000000000405741315563672100221760ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010-2011 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include "agent-helper.h" static const gchar *_bt_agent_introspect_xml = "\n\t\n\t\t\n\t\t\n\t\t\n\t\t\t\n\t\t\t\n\t\t\n\t\t\n\t\t\t\n\t\t\t\n\t\t\n\t\t\n\t\t\t\n\t\t\t\n\t\t\n\t\t\n\t\t\t\n\t\t\t\n\t\t\t\n\t\t\n\t\t\n\t\t\t\n\t\t\t\n\t\t\n\t\t\n\t\t\t\n\t\t\n\t\t\n\t\t\t\n\t\t\t\n\t\t\n\t\t\n\t\t\n\t\n\n"; static guint _bt_agent_registration_id = 0; static GHashTable *_pin_hash_table = NULL; static gboolean _interactive = TRUE; static GMainLoop *_mainloop = NULL; static void _bt_agent_g_destroy_notify(gpointer data); static void _bt_agent_method_call_func(GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *method_name, GVariant *parameters, GDBusMethodInvocation *invocation, gpointer user_data); static const gchar *_find_device_pin(const gchar *device_path); static void _bt_agent_method_call_func(GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *method_name, GVariant *parameters, GDBusMethodInvocation *invocation, gpointer user_data) { // g_print("%s%s\n", method_name, g_variant_print(parameters, FALSE)); if (g_strcmp0(method_name, "AuthorizeService") == 0) { GError *error = NULL; Device *device_obj = device_new(g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL)); const char *uuid = g_variant_get_string(g_variant_get_child_value(parameters, 1), NULL); if (_interactive) g_print("Device: %s (%s) for UUID %s\n", device_get_alias(device_obj, &error), device_get_address(device_obj, &error), uuid); if (error) { g_critical("Failed to get remote device's MAC address: %s", error->message); g_error_free(error); g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "Internal error occurred"); return; } if (device_get_paired (device_obj, &error)) { g_dbus_method_invocation_return_value(invocation, NULL); } else if (error) { g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "Internal error occurred"); g_error_free (error); } else { g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "Service authorization rejected"); } } else if (g_strcmp0(method_name, "Cancel") == 0) { if (_interactive) g_print("Request canceled\n"); // Return void g_dbus_method_invocation_return_value(invocation, NULL); } else if (g_strcmp0(method_name, "DisplayPasskey") == 0) { GError *error = NULL; Device *device_obj = device_new(g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL)); const gchar *pin = _find_device_pin(device_get_dbus_object_path(device_obj)); if (_interactive) g_print("Device: %s (%s)\n", device_get_alias(device_obj, &error), device_get_address(device_obj, &error)); if (error) { g_critical("Failed to get remote device's MAC address: %s", error->message); g_error_free(error); } g_object_unref(device_obj); if (_interactive) { g_print("Passkey: %u, entered: %u\n", g_variant_get_uint32(g_variant_get_child_value(parameters, 1)), g_variant_get_uint16(g_variant_get_child_value(parameters, 2))); g_dbus_method_invocation_return_value(invocation, NULL); return; } else if (pin != NULL) { /* OK, device found */ g_dbus_method_invocation_return_value(invocation, NULL); return; } g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "Pairing rejected"); } else if (g_strcmp0(method_name, "DisplayPinCode") == 0) { GError *error = NULL; Device *device_obj = device_new(g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL)); const gchar *pin = _find_device_pin(device_get_dbus_object_path(device_obj)); const gchar *pincode = g_variant_get_string(g_variant_get_child_value(parameters, 1), NULL); if (_interactive) g_print("Device: %s (%s)\n", device_get_alias(device_obj, &error), device_get_address(device_obj, &error)); if (error) { g_critical("Failed to get remote device's MAC address: %s", error->message); g_error_free(error); } g_object_unref(device_obj); /* Try to use found PIN */ if (pin != NULL) { if (g_strcmp0(pin, "*") == 0 || g_strcmp0(pin, pincode) == 0) { if (_interactive) g_print("Pin code confirmed\n"); g_dbus_method_invocation_return_value(invocation, NULL); } else g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "Passkey does not match"); return; } else if (_interactive) { g_print("Confirm pin code: %s (yes/no)? ", pincode); gchar yn[4] = {0,}; errno = 0; if (scanf("%3s", yn) == EOF && errno) g_warning("%s\n", strerror(errno)); if(g_ascii_strcasecmp(yn, "yes") == 0 || g_ascii_strcasecmp(yn, "y") == 0) g_dbus_method_invocation_return_value(invocation, NULL); else g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "Passkey does not match"); return; } g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "Pairing rejected"); } else if (g_strcmp0(method_name, "Release") == 0) { agent_need_unregister = FALSE; if(_mainloop) if (g_main_loop_is_running(_mainloop)) g_main_loop_quit(_mainloop); g_print("Agent released\n"); // Return void g_dbus_method_invocation_return_value(invocation, NULL); } else if (g_strcmp0(method_name, "RequestAuthorization") == 0) { GError *error = NULL; Device *device_obj = device_new(g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL)); if (_interactive) g_print("Device: %s (%s)\n", device_get_alias(device_obj, &error), device_get_address(device_obj, &error)); if(error) { g_critical("Failed to get remote device's MAC address: %s", error->message); g_error_free(error); } g_object_unref(device_obj); if (_interactive) { g_print("Authorize this device pairing (yes/no)? "); gchar yn[4] = {0,}; errno = 0; if (scanf("%3s", yn) == EOF && errno) g_warning("%s\n", strerror(errno)); if(g_ascii_strcasecmp(yn, "yes") == 0 || g_ascii_strcasecmp(yn, "y") == 0) g_dbus_method_invocation_return_value(invocation, NULL); else g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "Pairing rejected"); return; } g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "Pairing rejected"); } else if (g_strcmp0(method_name, "RequestConfirmation") == 0) { GError *error = NULL; Device *device_obj = device_new(g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL)); guint32 passkey = g_variant_get_uint32(g_variant_get_child_value(parameters, 1)); const gchar *pin = _find_device_pin(device_get_dbus_object_path(device_obj)); if (_interactive) g_print("Device: %s (%s)\n", device_get_alias(device_obj, &error), device_get_address(device_obj, &error)); if(error) { g_critical("Failed to get remote device's MAC address: %s", error->message); g_error_free(error); } g_object_unref(device_obj); /* Try to use found PIN */ if (pin != NULL) { guint32 passkey_t; sscanf(pin, "%u", &passkey_t); if (g_strcmp0(pin, "*") == 0 || passkey_t == passkey) { if (_interactive) g_print("Passkey confirmed\n"); g_dbus_method_invocation_return_value(invocation, NULL); } else g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "Passkey does not match"); return; } else if (_interactive) { g_print("Confirm passkey: %u (yes/no)? ", passkey); gchar yn[4] = {0,}; errno = 0; if (scanf("%3s", yn) == EOF && errno) g_warning("%s\n", strerror(errno)); if(g_ascii_strcasecmp(yn, "yes") == 0 || g_ascii_strcasecmp(yn, "y") == 0) g_dbus_method_invocation_return_value(invocation, NULL); else g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "Passkey does not match"); return; } g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "Passkey does not match"); } else if (g_strcmp0(method_name, "RequestPasskey") == 0) { GError *error = NULL; Device *device_obj = device_new(g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL)); const gchar *pin = _find_device_pin(device_get_dbus_object_path(device_obj)); guint32 ret = 0; gboolean invoke = FALSE; if (_interactive) g_print("Device: %s (%s)\n", device_get_alias(device_obj, &error), device_get_address(device_obj, &error)); if(error) { g_critical("Failed to get remote device's MAC address: %s", error->message); g_error_free(error); } g_object_unref(device_obj); /* Try to use found PIN */ if (pin != NULL) { if (_interactive) g_print("Passkey found\n"); sscanf(pin, "%u", &ret); invoke = TRUE; } else if (_interactive) { g_print("Enter passkey: "); errno = 0; if (scanf("%u", &ret) == EOF && errno) g_warning("%s\n", strerror(errno)); invoke = TRUE; } if (invoke) { g_dbus_method_invocation_return_value(invocation, g_variant_new ("(u)", ret)); } else { g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "No passkey inputted"); } } else if (g_strcmp0(method_name, "RequestPinCode") == 0) { GError *error = NULL; Device *device_obj = device_new(g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL)); const gchar *pin = _find_device_pin(device_get_dbus_object_path(device_obj)); gchar *ret = NULL; gboolean invoke = FALSE; if (_interactive) g_print("Device: %s (%s)\n", device_get_alias(device_obj, &error), device_get_address(device_obj, &error)); if(error) { g_critical("Failed to get remote device's MAC address: %s", error->message); g_error_free(error); } g_object_unref(device_obj); /* Try to use found PIN */ if (pin != NULL) { if (_interactive) g_print("Passkey found\n"); sscanf(pin, "%ms", &ret); invoke = TRUE; } else if (_interactive) { g_print("Enter passkey: "); errno = 0; if (scanf("%ms", &ret) == EOF && errno) g_warning("%s\n", strerror(errno)); invoke = TRUE; } if (invoke) { g_dbus_method_invocation_return_value(invocation, g_variant_new ("(s)", ret)); } else { g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.Error.Rejected", "No passkey inputted"); } if (ret) free(ret); } } static void _bt_agent_g_destroy_notify(gpointer data) { g_free(data); } static const gchar *_find_device_pin(const gchar *device_path) { if (_pin_hash_table) { GError *error = NULL; Device *device = device_new(device_path); const gchar *pin_by_addr = g_hash_table_lookup(_pin_hash_table, device_get_address(device, &error)); const gchar *pin_by_alias = g_hash_table_lookup(_pin_hash_table, device_get_alias(device, &error)); if(error) { g_critical("Failed to get remote device's MAC address: %s", error->message); g_error_free(error); } g_object_unref(device); const gchar *pin_all = g_hash_table_lookup(_pin_hash_table, "*"); if (pin_by_addr) return pin_by_addr; else if (pin_by_alias) return pin_by_alias; else if (pin_all) return pin_all; } return NULL; } void register_agent_callbacks(gboolean interactive_console, GHashTable *pin_dictonary, gpointer main_loop_object, GError **error) { GDBusInterfaceVTable bt_agent_table; memset(&bt_agent_table, 0x0, sizeof(bt_agent_table)); if(pin_dictonary) _pin_hash_table = pin_dictonary; if(main_loop_object) _mainloop = (GMainLoop *) main_loop_object; _interactive = interactive_console; GDBusNodeInfo *bt_agent_node_info = g_dbus_node_info_new_for_xml(_bt_agent_introspect_xml, error); GDBusInterfaceInfo *bt_agent_interface_info = g_dbus_node_info_lookup_interface(bt_agent_node_info, AGENT_DBUS_INTERFACE); bt_agent_table.method_call = _bt_agent_method_call_func; _bt_agent_registration_id = g_dbus_connection_register_object(g_bus_get_sync(G_BUS_TYPE_SYSTEM, NULL, error), AGENT_PATH, bt_agent_interface_info, &bt_agent_table, NULL, _bt_agent_g_destroy_notify, error); g_dbus_node_info_unref(bt_agent_node_info); } void unregister_agent_callbacks(GError **error) { if (_bt_agent_registration_id) g_dbus_connection_unregister_object(g_bus_get_sync(G_BUS_TYPE_SYSTEM, NULL, error), _bt_agent_registration_id); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/agent-helper.h000066400000000000000000000025351315563672100221760ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __AGENT_HELPER_H #define __AGENT_HELPER_H #ifdef __cplusplus extern "C" { #endif #include #include "bluez-api.h" #define AGENT_DBUS_INTERFACE "org.bluez.Agent1" #define AGENT_PATH "/org/blueztools" gboolean agent_need_unregister; void register_agent_callbacks(gboolean interactive_console, GHashTable *pin_dictonary, gpointer main_loop_object, GError **error); void unregister_agent_callbacks(GError **error); #ifdef __cplusplus } #endif #endif /* __AGENT_HELPER_H */bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez-api.h000066400000000000000000000027741315563672100215200ustar00rootroot00000000000000#ifndef BLUEZ_API_H #define BLUEZ_API_H #ifdef __cplusplus extern "C" { #endif #define BLUEZ_DBUS_SERVICE_NAME "org.bluez" #define BLUEZ_OBEX_DBUS_SERVICE_NAME "org.bluez.obex" #define BLUEZ_DBUS_BASE_PATH "/org/bluez" #define BLUEZ_OBEX_DBUS_BASE_PATH "/org/bluez/obex" #include "manager.h" #include "obex_agent.h" #include "bluez/adapter.h" #include "bluez/agent_manager.h" #include "bluez/alert.h" #include "bluez/alert_agent.h" #include "bluez/cycling_speed.h" #include "bluez/cycling_speed_manager.h" #include "bluez/device.h" #include "bluez/health_channel.h" #include "bluez/health_device.h" #include "bluez/health_manager.h" #include "bluez/heart_rate.h" #include "bluez/heart_rate_manager.h" #include "bluez/media.h" #include "bluez/media_control.h" #include "bluez/media_player.h" #include "bluez/network.h" #include "bluez/network_server.h" #include "bluez/obex/obex_agent_manager.h" #include "bluez/obex/obex_client.h" #include "bluez/obex/obex_file_transfer.h" #include "bluez/obex/obex_message.h" #include "bluez/obex/obex_message_access.h" #include "bluez/obex/obex_object_push.h" #include "bluez/obex/obex_phonebook_access.h" #include "bluez/obex/obex_session.h" #include "bluez/obex/obex_synchronization.h" #include "bluez/obex/obex_transfer.h" #include "bluez/profile_manager.h" #include "bluez/proximity_monitor.h" #include "bluez/proximity_reporter.h" #include "bluez/sim_access.h" #include "bluez/thermometer.h" #include "bluez/thermometer_manager.h" #ifdef __cplusplus } #endif #endif /* BLUEZ_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/000077500000000000000000000000001315563672100205665ustar00rootroot00000000000000bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/adapter.c000066400000000000000000000277451315563672100223710ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "adapter.h" #define ADAPTER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), ADAPTER_TYPE, AdapterPrivate)) struct _AdapterPrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(Adapter, adapter, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _adapter_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _adapter_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _adapter_create_gdbus_proxy(Adapter *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void adapter_dispose(GObject *gobject) { Adapter *self = ADAPTER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(adapter_parent_class)->dispose(gobject); } static void adapter_finalize (GObject *gobject) { Adapter *self = ADAPTER(gobject); G_OBJECT_CLASS(adapter_parent_class)->finalize(gobject); } static void adapter_class_init(AdapterClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = adapter_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _adapter_get_property; gobject_class->set_property = _adapter_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "Adapter D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void adapter_init(Adapter *self) { self->priv = adapter_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _adapter_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { Adapter *self = ADAPTER(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, adapter_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _adapter_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { Adapter *self = ADAPTER(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _adapter_create_gdbus_proxy(self, ADAPTER_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ Adapter *adapter_new(const gchar *dbus_object_path) { return g_object_new(ADAPTER_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _adapter_create_gdbus_proxy(Adapter *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(ADAPTER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, ADAPTER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "system", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *adapter_get_dbus_object_path(Adapter *self) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* void RemoveDevice(object device) */ void adapter_remove_device(Adapter *self, const gchar *device, GError **error) { g_assert(ADAPTER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "RemoveDevice", g_variant_new ("(o)", device), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void StartDiscovery() */ void adapter_start_discovery(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "StartDiscovery", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void StopDiscovery() */ void adapter_stop_discovery(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "StopDiscovery", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* Properties access methods */ GVariant *adapter_get_properties(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, ADAPTER_DBUS_INTERFACE, error); } void adapter_set_property(Adapter *self, const gchar *name, const GVariant *value, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, ADAPTER_DBUS_INTERFACE, name, value, error); } const gchar *adapter_get_address(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, ADAPTER_DBUS_INTERFACE, "Address", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *adapter_get_alias(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, ADAPTER_DBUS_INTERFACE, "Alias", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } void adapter_set_alias(Adapter *self, const gchar *value, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, ADAPTER_DBUS_INTERFACE, "Alias", g_variant_new_string(value), error); } guint32 adapter_get_class(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, ADAPTER_DBUS_INTERFACE, "Class", error); if(prop == NULL) return 0; guint32 ret = g_variant_get_uint32(prop); g_variant_unref(prop); return ret; } gboolean adapter_get_discoverable(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, ADAPTER_DBUS_INTERFACE, "Discoverable", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } void adapter_set_discoverable(Adapter *self, const gboolean value, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, ADAPTER_DBUS_INTERFACE, "Discoverable", g_variant_new_boolean(value), error); } guint32 adapter_get_discoverable_timeout(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, ADAPTER_DBUS_INTERFACE, "DiscoverableTimeout", error); if(prop == NULL) return 0; guint32 ret = g_variant_get_uint32(prop); g_variant_unref(prop); return ret; } void adapter_set_discoverable_timeout(Adapter *self, const guint32 value, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, ADAPTER_DBUS_INTERFACE, "DiscoverableTimeout", g_variant_new_uint32(value), error); } gboolean adapter_get_discovering(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, ADAPTER_DBUS_INTERFACE, "Discovering", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } const gchar *adapter_get_modalias(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, ADAPTER_DBUS_INTERFACE, "Modalias", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *adapter_get_name(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, ADAPTER_DBUS_INTERFACE, "Name", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } gboolean adapter_get_pairable(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, ADAPTER_DBUS_INTERFACE, "Pairable", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } void adapter_set_pairable(Adapter *self, const gboolean value, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, ADAPTER_DBUS_INTERFACE, "Pairable", g_variant_new_boolean(value), error); } guint32 adapter_get_pairable_timeout(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, ADAPTER_DBUS_INTERFACE, "PairableTimeout", error); if(prop == NULL) return 0; guint32 ret = g_variant_get_uint32(prop); g_variant_unref(prop); return ret; } void adapter_set_pairable_timeout(Adapter *self, const guint32 value, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, ADAPTER_DBUS_INTERFACE, "PairableTimeout", g_variant_new_uint32(value), error); } gboolean adapter_get_powered(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, ADAPTER_DBUS_INTERFACE, "Powered", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } void adapter_set_powered(Adapter *self, const gboolean value, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, ADAPTER_DBUS_INTERFACE, "Powered", g_variant_new_boolean(value), error); } const gchar **adapter_get_uuids(Adapter *self, GError **error) { g_assert(ADAPTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, ADAPTER_DBUS_INTERFACE, "UUIDs", error); if(prop == NULL) return NULL; const gchar **ret = g_variant_get_strv(prop, NULL); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/adapter.h000066400000000000000000000073001315563672100223570ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __ADAPTER_H #define __ADAPTER_H #ifdef __cplusplus extern "C" { #endif #include #define ADAPTER_DBUS_SERVICE "org.bluez" #define ADAPTER_DBUS_INTERFACE "org.bluez.Adapter1" /* * Type macros */ #define ADAPTER_TYPE (adapter_get_type()) #define ADAPTER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), ADAPTER_TYPE, Adapter)) #define ADAPTER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), ADAPTER_TYPE)) #define ADAPTER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), ADAPTER_TYPE, AdapterClass)) #define ADAPTER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), ADAPTER_TYPE)) #define ADAPTER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), ADAPTER_TYPE, AdapterClass)) typedef struct _Adapter Adapter; typedef struct _AdapterClass AdapterClass; typedef struct _AdapterPrivate AdapterPrivate; struct _Adapter { GObject parent_instance; /*< private >*/ AdapterPrivate *priv; }; struct _AdapterClass { GObjectClass parent_class; }; /* used by ADAPTER_TYPE */ GType adapter_get_type(void) G_GNUC_CONST; /* * Constructor */ Adapter *adapter_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *adapter_get_dbus_object_path(Adapter *self); void adapter_remove_device(Adapter *self, const gchar *device, GError **error); void adapter_start_discovery(Adapter *self, GError **error); void adapter_stop_discovery(Adapter *self, GError **error); GVariant *adapter_get_properties(Adapter *self, GError **error); void adapter_set_property(Adapter *self, const gchar *name, const GVariant *value, GError **error); const gchar *adapter_get_address(Adapter *self, GError **error); const gchar *adapter_get_alias(Adapter *self, GError **error); void adapter_set_alias(Adapter *self, const gchar *value, GError **error); guint32 adapter_get_class(Adapter *self, GError **error); gboolean adapter_get_discoverable(Adapter *self, GError **error); void adapter_set_discoverable(Adapter *self, const gboolean value, GError **error); guint32 adapter_get_discoverable_timeout(Adapter *self, GError **error); void adapter_set_discoverable_timeout(Adapter *self, const guint32 value, GError **error); gboolean adapter_get_discovering(Adapter *self, GError **error); const gchar *adapter_get_modalias(Adapter *self, GError **error); const gchar *adapter_get_name(Adapter *self, GError **error); gboolean adapter_get_pairable(Adapter *self, GError **error); void adapter_set_pairable(Adapter *self, const gboolean value, GError **error); guint32 adapter_get_pairable_timeout(Adapter *self, GError **error); void adapter_set_pairable_timeout(Adapter *self, const guint32 value, GError **error); gboolean adapter_get_powered(Adapter *self, GError **error); void adapter_set_powered(Adapter *self, const gboolean value, GError **error); const gchar **adapter_get_uuids(Adapter *self, GError **error); #ifdef __cplusplus } #endif #endif /* __ADAPTER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/agent_manager.c000066400000000000000000000116721315563672100235310ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "agent_manager.h" #define AGENT_MANAGER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), AGENT_MANAGER_TYPE, AgentManagerPrivate)) struct _AgentManagerPrivate { GDBusProxy *proxy; }; G_DEFINE_TYPE_WITH_PRIVATE(AgentManager, agent_manager, G_TYPE_OBJECT); enum { PROP_0, }; static void _agent_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _agent_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _agent_manager_create_gdbus_proxy(AgentManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void agent_manager_dispose(GObject *gobject) { AgentManager *self = AGENT_MANAGER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Chain up to the parent class */ G_OBJECT_CLASS(agent_manager_parent_class)->dispose(gobject); } static void agent_manager_finalize (GObject *gobject) { AgentManager *self = AGENT_MANAGER(gobject); G_OBJECT_CLASS(agent_manager_parent_class)->finalize(gobject); } static void agent_manager_class_init(AgentManagerClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = agent_manager_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _agent_manager_get_property; gobject_class->set_property = _agent_manager_set_property; if (pspec) g_param_spec_unref(pspec); } static void agent_manager_init(AgentManager *self) { self->priv = agent_manager_get_instance_private (self); self->priv->proxy = NULL; g_assert(system_conn != NULL); GError *error = NULL; _agent_manager_create_gdbus_proxy(self, AGENT_MANAGER_DBUS_SERVICE, AGENT_MANAGER_DBUS_PATH, &error); g_assert(error == NULL); } static void _agent_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { AgentManager *self = AGENT_MANAGER(object); switch (property_id) { default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _agent_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { AgentManager *self = AGENT_MANAGER(object); GError *error = NULL; switch (property_id) { default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ AgentManager *agent_manager_new() { return g_object_new(AGENT_MANAGER_TYPE, NULL); } /* Private DBus proxy creation */ static void _agent_manager_create_gdbus_proxy(AgentManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(AGENT_MANAGER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, AGENT_MANAGER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* void RegisterAgent(object agent, string capability) */ void agent_manager_register_agent(AgentManager *self, const gchar *agent, const gchar *capability, GError **error) { g_assert(AGENT_MANAGER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "RegisterAgent", g_variant_new ("(os)", agent, capability), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void RequestDefaultAgent(object agent) */ void agent_manager_request_default_agent(AgentManager *self, const gchar *agent, GError **error) { g_assert(AGENT_MANAGER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "RequestDefaultAgent", g_variant_new ("(o)", agent), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void UnregisterAgent(object agent) */ void agent_manager_unregister_agent(AgentManager *self, const gchar *agent, GError **error) { g_assert(AGENT_MANAGER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "UnregisterAgent", g_variant_new ("(o)", agent), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/agent_manager.h000066400000000000000000000050401315563672100235260ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __AGENT_MANAGER_H #define __AGENT_MANAGER_H #ifdef __cplusplus extern "C" { #endif #include #define AGENT_MANAGER_DBUS_SERVICE "org.bluez" #define AGENT_MANAGER_DBUS_INTERFACE "org.bluez.AgentManager1" #define AGENT_MANAGER_DBUS_PATH "/org/bluez" /* * Type macros */ #define AGENT_MANAGER_TYPE (agent_manager_get_type()) #define AGENT_MANAGER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), AGENT_MANAGER_TYPE, AgentManager)) #define AGENT_MANAGER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), AGENT_MANAGER_TYPE)) #define AGENT_MANAGER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), AGENT_MANAGER_TYPE, AgentManagerClass)) #define AGENT_MANAGER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), AGENT_MANAGER_TYPE)) #define AGENT_MANAGER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), AGENT_MANAGER_TYPE, AgentManagerClass)) typedef struct _AgentManager AgentManager; typedef struct _AgentManagerClass AgentManagerClass; typedef struct _AgentManagerPrivate AgentManagerPrivate; struct _AgentManager { GObject parent_instance; /*< private >*/ AgentManagerPrivate *priv; }; struct _AgentManagerClass { GObjectClass parent_class; }; /* used by AGENT_MANAGER_TYPE */ GType agent_manager_get_type(void) G_GNUC_CONST; /* * Constructor */ AgentManager *agent_manager_new(); /* * Method definitions */ void agent_manager_register_agent(AgentManager *self, const gchar *agent, const gchar *capability, GError **error); void agent_manager_request_default_agent(AgentManager *self, const gchar *agent, GError **error); void agent_manager_unregister_agent(AgentManager *self, const gchar *agent, GError **error); #ifdef __cplusplus } #endif #endif /* __AGENT_MANAGER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/alert.c000066400000000000000000000112311315563672100220370ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "alert.h" #define ALERT_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), ALERT_TYPE, AlertPrivate)) struct _AlertPrivate { GDBusProxy *proxy; }; G_DEFINE_TYPE_WITH_PRIVATE(Alert, alert, G_TYPE_OBJECT); enum { PROP_0, }; static void _alert_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _alert_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _alert_create_gdbus_proxy(Alert *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void alert_dispose(GObject *gobject) { Alert *self = ALERT(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Chain up to the parent class */ G_OBJECT_CLASS(alert_parent_class)->dispose(gobject); } static void alert_finalize (GObject *gobject) { Alert *self = ALERT(gobject); G_OBJECT_CLASS(alert_parent_class)->finalize(gobject); } static void alert_class_init(AlertClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = alert_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _alert_get_property; gobject_class->set_property = _alert_set_property; if (pspec) g_param_spec_unref(pspec); } static void alert_init(Alert *self) { self->priv = alert_get_instance_private (self); self->priv->proxy = NULL; g_assert(system_conn != NULL); GError *error = NULL; _alert_create_gdbus_proxy(self, ALERT_DBUS_SERVICE, ALERT_DBUS_PATH, &error); g_assert(error == NULL); } static void _alert_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { Alert *self = ALERT(object); switch (property_id) { default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _alert_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { Alert *self = ALERT(object); GError *error = NULL; switch (property_id) { default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ Alert *alert_new() { return g_object_new(ALERT_TYPE, NULL); } /* Private DBus proxy creation */ static void _alert_create_gdbus_proxy(Alert *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(ALERT_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, ALERT_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* void NewAlert(string category, uint16 count, string description) */ void alert_new_alert(Alert *self, const gchar *category, const guint16 count, const gchar *description, GError **error) { g_assert(ALERT_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "NewAlert", g_variant_new ("(sqs)", category, count, description), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void RegisterAlert(string category, object agent) */ void alert_register_alert(Alert *self, const gchar *category, const gchar *agent, GError **error) { g_assert(ALERT_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "RegisterAlert", g_variant_new ("(so)", category, agent), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void UnreadAlert(string category, uint16 count) */ void alert_unread_alert(Alert *self, const gchar *category, const guint16 count, GError **error) { g_assert(ALERT_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "UnreadAlert", g_variant_new ("(sq)", category, count), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/alert.h000066400000000000000000000044411315563672100220510ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __ALERT_H #define __ALERT_H #ifdef __cplusplus extern "C" { #endif #include #define ALERT_DBUS_SERVICE "org.bluez" #define ALERT_DBUS_INTERFACE "org.bluez.Alert1" #define ALERT_DBUS_PATH "/org/bluez" /* * Type macros */ #define ALERT_TYPE (alert_get_type()) #define ALERT(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), ALERT_TYPE, Alert)) #define ALERT_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), ALERT_TYPE)) #define ALERT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), ALERT_TYPE, AlertClass)) #define ALERT_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), ALERT_TYPE)) #define ALERT_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), ALERT_TYPE, AlertClass)) typedef struct _Alert Alert; typedef struct _AlertClass AlertClass; typedef struct _AlertPrivate AlertPrivate; struct _Alert { GObject parent_instance; /*< private >*/ AlertPrivate *priv; }; struct _AlertClass { GObjectClass parent_class; }; /* used by ALERT_TYPE */ GType alert_get_type(void) G_GNUC_CONST; /* * Constructor */ Alert *alert_new(); /* * Method definitions */ void alert_new_alert(Alert *self, const gchar *category, const guint16 count, const gchar *description, GError **error); void alert_register_alert(Alert *self, const gchar *category, const gchar *agent, GError **error); void alert_unread_alert(Alert *self, const gchar *category, const guint16 count, GError **error); #ifdef __cplusplus } #endif #endif /* __ALERT_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/alert_agent.c000066400000000000000000000127421315563672100232250ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "alert_agent.h" #define ALERT_AGENT_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), ALERT_AGENT_TYPE, AlertAgentPrivate)) struct _AlertAgentPrivate { GDBusProxy *proxy; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(AlertAgent, alert_agent, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _alert_agent_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _alert_agent_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _alert_agent_create_gdbus_proxy(AlertAgent *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void alert_agent_dispose(GObject *gobject) { AlertAgent *self = ALERT_AGENT(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(alert_agent_parent_class)->dispose(gobject); } static void alert_agent_finalize (GObject *gobject) { AlertAgent *self = ALERT_AGENT(gobject); G_OBJECT_CLASS(alert_agent_parent_class)->finalize(gobject); } static void alert_agent_class_init(AlertAgentClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = alert_agent_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _alert_agent_get_property; gobject_class->set_property = _alert_agent_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "AlertAgent D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void alert_agent_init(AlertAgent *self) { self->priv = alert_agent_get_instance_private (self); self->priv->proxy = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _alert_agent_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { AlertAgent *self = ALERT_AGENT(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, alert_agent_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _alert_agent_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { AlertAgent *self = ALERT_AGENT(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _alert_agent_create_gdbus_proxy(self, ALERT_AGENT_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ AlertAgent *alert_agent_new(const gchar *dbus_object_path) { return g_object_new(ALERT_AGENT_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _alert_agent_create_gdbus_proxy(AlertAgent *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(ALERT_AGENT_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, ALERT_AGENT_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* Get DBus object path */ const gchar *alert_agent_get_dbus_object_path(AlertAgent *self) { g_assert(ALERT_AGENT_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* void MuteOnce() */ void alert_agent_mute_once(AlertAgent *self, GError **error) { g_assert(ALERT_AGENT_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "MuteOnce", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Release() */ void alert_agent_release(AlertAgent *self, GError **error) { g_assert(ALERT_AGENT_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Release", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void SetRinger(string mode) */ void alert_agent_set_ringer(AlertAgent *self, const gchar *mode, GError **error) { g_assert(ALERT_AGENT_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "SetRinger", g_variant_new ("(s)", mode), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/alert_agent.h000066400000000000000000000046471315563672100232370ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __ALERT_AGENT_H #define __ALERT_AGENT_H #ifdef __cplusplus extern "C" { #endif #include #define ALERT_AGENT_DBUS_SERVICE "org.bluez" #define ALERT_AGENT_DBUS_INTERFACE "org.bluez.AlertAgent1" /* * Type macros */ #define ALERT_AGENT_TYPE (alert_agent_get_type()) #define ALERT_AGENT(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), ALERT_AGENT_TYPE, AlertAgent)) #define ALERT_AGENT_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), ALERT_AGENT_TYPE)) #define ALERT_AGENT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), ALERT_AGENT_TYPE, AlertAgentClass)) #define ALERT_AGENT_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), ALERT_AGENT_TYPE)) #define ALERT_AGENT_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), ALERT_AGENT_TYPE, AlertAgentClass)) typedef struct _AlertAgent AlertAgent; typedef struct _AlertAgentClass AlertAgentClass; typedef struct _AlertAgentPrivate AlertAgentPrivate; struct _AlertAgent { GObject parent_instance; /*< private >*/ AlertAgentPrivate *priv; }; struct _AlertAgentClass { GObjectClass parent_class; }; /* used by ALERT_AGENT_TYPE */ GType alert_agent_get_type(void) G_GNUC_CONST; /* * Constructor */ AlertAgent *alert_agent_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *alert_agent_get_dbus_object_path(AlertAgent *self); void alert_agent_mute_once(AlertAgent *self, GError **error); void alert_agent_release(AlertAgent *self, GError **error); void alert_agent_set_ringer(AlertAgent *self, const gchar *mode, GError **error); #ifdef __cplusplus } #endif #endif /* __ALERT_AGENT_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/cycling_speed.c000066400000000000000000000150531315563672100235460ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "cycling_speed.h" #define CYCLING_SPEED_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), CYCLING_SPEED_TYPE, CyclingSpeedPrivate)) struct _CyclingSpeedPrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(CyclingSpeed, cycling_speed, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _cycling_speed_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _cycling_speed_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _cycling_speed_create_gdbus_proxy(CyclingSpeed *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void cycling_speed_dispose(GObject *gobject) { CyclingSpeed *self = CYCLING_SPEED(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(cycling_speed_parent_class)->dispose(gobject); } static void cycling_speed_finalize (GObject *gobject) { CyclingSpeed *self = CYCLING_SPEED(gobject); G_OBJECT_CLASS(cycling_speed_parent_class)->finalize(gobject); } static void cycling_speed_class_init(CyclingSpeedClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = cycling_speed_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _cycling_speed_get_property; gobject_class->set_property = _cycling_speed_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "CyclingSpeed D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void cycling_speed_init(CyclingSpeed *self) { self->priv = cycling_speed_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _cycling_speed_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { CyclingSpeed *self = CYCLING_SPEED(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, cycling_speed_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _cycling_speed_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { CyclingSpeed *self = CYCLING_SPEED(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _cycling_speed_create_gdbus_proxy(self, CYCLING_SPEED_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ CyclingSpeed *cycling_speed_new(const gchar *dbus_object_path) { return g_object_new(CYCLING_SPEED_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _cycling_speed_create_gdbus_proxy(CyclingSpeed *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(CYCLING_SPEED_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, CYCLING_SPEED_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "system", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *cycling_speed_get_dbus_object_path(CyclingSpeed *self) { g_assert(CYCLING_SPEED_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* Properties access methods */ GVariant *cycling_speed_get_properties(CyclingSpeed *self, GError **error) { g_assert(CYCLING_SPEED_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, CYCLING_SPEED_DBUS_INTERFACE, error); } void cycling_speed_set_property(CyclingSpeed *self, const gchar *name, const GVariant *value, GError **error) { g_assert(CYCLING_SPEED_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, CYCLING_SPEED_DBUS_INTERFACE, name, value, error); } gboolean cycling_speed_get_multiple_locations_supported(CyclingSpeed *self, GError **error) { g_assert(CYCLING_SPEED_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, CYCLING_SPEED_DBUS_INTERFACE, "MultipleLocationsSupported", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } gboolean cycling_speed_get_wheel_revolution_data_supported(CyclingSpeed *self, GError **error) { g_assert(CYCLING_SPEED_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, CYCLING_SPEED_DBUS_INTERFACE, "WheelRevolutionDataSupported", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/cycling_speed.h000066400000000000000000000052341315563672100235530ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __CYCLING_SPEED_H #define __CYCLING_SPEED_H #ifdef __cplusplus extern "C" { #endif #include #define CYCLING_SPEED_DBUS_SERVICE "org.bluez" #define CYCLING_SPEED_DBUS_INTERFACE "org.bluez.CyclingSpeed1" /* * Type macros */ #define CYCLING_SPEED_TYPE (cycling_speed_get_type()) #define CYCLING_SPEED(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), CYCLING_SPEED_TYPE, CyclingSpeed)) #define CYCLING_SPEED_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), CYCLING_SPEED_TYPE)) #define CYCLING_SPEED_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), CYCLING_SPEED_TYPE, CyclingSpeedClass)) #define CYCLING_SPEED_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), CYCLING_SPEED_TYPE)) #define CYCLING_SPEED_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), CYCLING_SPEED_TYPE, CyclingSpeedClass)) typedef struct _CyclingSpeed CyclingSpeed; typedef struct _CyclingSpeedClass CyclingSpeedClass; typedef struct _CyclingSpeedPrivate CyclingSpeedPrivate; struct _CyclingSpeed { GObject parent_instance; /*< private >*/ CyclingSpeedPrivate *priv; }; struct _CyclingSpeedClass { GObjectClass parent_class; }; /* used by CYCLING_SPEED_TYPE */ GType cycling_speed_get_type(void) G_GNUC_CONST; /* * Constructor */ CyclingSpeed *cycling_speed_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *cycling_speed_get_dbus_object_path(CyclingSpeed *self); GVariant *cycling_speed_get_properties(CyclingSpeed *self, GError **error); void cycling_speed_set_property(CyclingSpeed *self, const gchar *name, const GVariant *value, GError **error); gboolean cycling_speed_get_multiple_locations_supported(CyclingSpeed *self, GError **error); gboolean cycling_speed_get_wheel_revolution_data_supported(CyclingSpeed *self, GError **error); #ifdef __cplusplus } #endif #endif /* __CYCLING_SPEED_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/cycling_speed_manager.c000066400000000000000000000123261315563672100252400ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "cycling_speed_manager.h" #define CYCLING_SPEED_MANAGER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), CYCLING_SPEED_MANAGER_TYPE, CyclingSpeedManagerPrivate)) struct _CyclingSpeedManagerPrivate { GDBusProxy *proxy; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(CyclingSpeedManager, cycling_speed_manager, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _cycling_speed_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _cycling_speed_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _cycling_speed_manager_create_gdbus_proxy(CyclingSpeedManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void cycling_speed_manager_dispose(GObject *gobject) { CyclingSpeedManager *self = CYCLING_SPEED_MANAGER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(cycling_speed_manager_parent_class)->dispose(gobject); } static void cycling_speed_manager_finalize (GObject *gobject) { CyclingSpeedManager *self = CYCLING_SPEED_MANAGER(gobject); G_OBJECT_CLASS(cycling_speed_manager_parent_class)->finalize(gobject); } static void cycling_speed_manager_class_init(CyclingSpeedManagerClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = cycling_speed_manager_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _cycling_speed_manager_get_property; gobject_class->set_property = _cycling_speed_manager_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "CyclingSpeedManager D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void cycling_speed_manager_init(CyclingSpeedManager *self) { self->priv = cycling_speed_manager_get_instance_private (self); self->priv->proxy = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _cycling_speed_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { CyclingSpeedManager *self = CYCLING_SPEED_MANAGER(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, cycling_speed_manager_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _cycling_speed_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { CyclingSpeedManager *self = CYCLING_SPEED_MANAGER(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _cycling_speed_manager_create_gdbus_proxy(self, CYCLING_SPEED_MANAGER_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ CyclingSpeedManager *cycling_speed_manager_new(const gchar *dbus_object_path) { return g_object_new(CYCLING_SPEED_MANAGER_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _cycling_speed_manager_create_gdbus_proxy(CyclingSpeedManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(CYCLING_SPEED_MANAGER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, CYCLING_SPEED_MANAGER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* Get DBus object path */ const gchar *cycling_speed_manager_get_dbus_object_path(CyclingSpeedManager *self) { g_assert(CYCLING_SPEED_MANAGER_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/cycling_speed_manager.h000066400000000000000000000050251315563672100252430ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __CYCLING_SPEED_MANAGER_H #define __CYCLING_SPEED_MANAGER_H #ifdef __cplusplus extern "C" { #endif #include #define CYCLING_SPEED_MANAGER_DBUS_SERVICE "org.bluez" #define CYCLING_SPEED_MANAGER_DBUS_INTERFACE "org.bluez.CyclingSpeedManager1" /* * Type macros */ #define CYCLING_SPEED_MANAGER_TYPE (cycling_speed_manager_get_type()) #define CYCLING_SPEED_MANAGER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), CYCLING_SPEED_MANAGER_TYPE, CyclingSpeedManager)) #define CYCLING_SPEED_MANAGER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), CYCLING_SPEED_MANAGER_TYPE)) #define CYCLING_SPEED_MANAGER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), CYCLING_SPEED_MANAGER_TYPE, CyclingSpeedManagerClass)) #define CYCLING_SPEED_MANAGER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), CYCLING_SPEED_MANAGER_TYPE)) #define CYCLING_SPEED_MANAGER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), CYCLING_SPEED_MANAGER_TYPE, CyclingSpeedManagerClass)) typedef struct _CyclingSpeedManager CyclingSpeedManager; typedef struct _CyclingSpeedManagerClass CyclingSpeedManagerClass; typedef struct _CyclingSpeedManagerPrivate CyclingSpeedManagerPrivate; struct _CyclingSpeedManager { GObject parent_instance; /*< private >*/ CyclingSpeedManagerPrivate *priv; }; struct _CyclingSpeedManagerClass { GObjectClass parent_class; }; /* used by CYCLING_SPEED_MANAGER_TYPE */ GType cycling_speed_manager_get_type(void) G_GNUC_CONST; /* * Constructor */ CyclingSpeedManager *cycling_speed_manager_new(const gchar *dbus_object_path); const gchar *cycling_speed_manager_get_dbus_object_path(CyclingSpeedManager *self); #ifdef __cplusplus } #endif #endif /* __CYCLING_SPEED_MANAGER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/device.c000066400000000000000000000325531315563672100222010ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "device.h" #define DEVICE_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), DEVICE_TYPE, DevicePrivate)) struct _DevicePrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(Device, device, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _device_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _device_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _device_create_gdbus_proxy(Device *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void device_dispose(GObject *gobject) { Device *self = DEVICE(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(device_parent_class)->dispose(gobject); } static void device_finalize (GObject *gobject) { Device *self = DEVICE(gobject); G_OBJECT_CLASS(device_parent_class)->finalize(gobject); } static void device_class_init(DeviceClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = device_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _device_get_property; gobject_class->set_property = _device_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "Device D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void device_init(Device *self) { self->priv = device_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _device_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { Device *self = DEVICE(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, device_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _device_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { Device *self = DEVICE(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _device_create_gdbus_proxy(self, DEVICE_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ Device *device_new(const gchar *dbus_object_path) { return g_object_new(DEVICE_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _device_create_gdbus_proxy(Device *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(DEVICE_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, DEVICE_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "system", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *device_get_dbus_object_path(Device *self) { g_assert(DEVICE_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* void CancelPairing() */ void device_cancel_pairing(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "CancelPairing", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Connect() */ void device_connect(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Connect", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void ConnectProfile(string uuid) */ void device_connect_profile(Device *self, const gchar *uuid, GError **error) { g_assert(DEVICE_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "ConnectProfile", g_variant_new ("(s)", uuid), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Disconnect() */ void device_disconnect(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Disconnect", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void DisconnectProfile(string uuid) */ void device_disconnect_profile(Device *self, const gchar *uuid, GError **error) { g_assert(DEVICE_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "DisconnectProfile", g_variant_new ("(s)", uuid), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Pair() */ void device_pair(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Pair", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* asynchronous call to void Pair() */ void device_pair_async(Device *self, GAsyncReadyCallback callback, gpointer user_data) { g_assert(DEVICE_IS(self)); g_dbus_proxy_call (self->priv->proxy, "Pair", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, callback, user_data); } /* finish asynchronous call to void Pair() */ void device_pair_finish(Device *self, GAsyncResult *res, GError **error) { g_assert(DEVICE_IS(self)); g_dbus_proxy_call_finish (self->priv->proxy, res, error); } /* Properties access methods */ GVariant *device_get_properties(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, DEVICE_DBUS_INTERFACE, error); } void device_set_property(Device *self, const gchar *name, const GVariant *value, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, DEVICE_DBUS_INTERFACE, name, value, error); } const gchar *device_get_adapter(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "Adapter", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *device_get_address(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "Address", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *device_get_alias(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "Alias", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } void device_set_alias(Device *self, const gchar *value, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, DEVICE_DBUS_INTERFACE, "Alias", g_variant_new_string(value), error); } guint16 device_get_appearance(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "Appearance", error); if(prop == NULL) return 0; guint16 ret = g_variant_get_uint16(prop); g_variant_unref(prop); return ret; } gboolean device_get_blocked(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "Blocked", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } void device_set_blocked(Device *self, const gboolean value, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, DEVICE_DBUS_INTERFACE, "Blocked", g_variant_new_boolean(value), error); } guint32 device_get_class(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "Class", error); if(prop == NULL) return 0; guint32 ret = g_variant_get_uint32(prop); g_variant_unref(prop); return ret; } gboolean device_get_connected(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "Connected", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } const gchar *device_get_icon(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "Icon", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } gboolean device_get_legacy_pairing(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "LegacyPairing", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } const gchar *device_get_modalias(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "Modalias", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *device_get_name(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "Name", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } gboolean device_get_paired(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "Paired", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } gint16 device_get_rssi(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "RSSI", error); if(prop == NULL) return 0; gint16 ret = g_variant_get_int16(prop); g_variant_unref(prop); return ret; } gboolean device_get_trusted(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "Trusted", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } void device_set_trusted(Device *self, const gboolean value, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, DEVICE_DBUS_INTERFACE, "Trusted", g_variant_new_boolean(value), error); } const gchar **device_get_uuids(Device *self, GError **error) { g_assert(DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, DEVICE_DBUS_INTERFACE, "UUIDs", error); if(prop == NULL) return NULL; const gchar **ret = g_variant_get_strv(prop, NULL); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/device.h000066400000000000000000000075331315563672100222060ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __DEVICE_H #define __DEVICE_H #ifdef __cplusplus extern "C" { #endif #include #define DEVICE_DBUS_SERVICE "org.bluez" #define DEVICE_DBUS_INTERFACE "org.bluez.Device1" /* * Type macros */ #define DEVICE_TYPE (device_get_type()) #define DEVICE(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), DEVICE_TYPE, Device)) #define DEVICE_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), DEVICE_TYPE)) #define DEVICE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), DEVICE_TYPE, DeviceClass)) #define DEVICE_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), DEVICE_TYPE)) #define DEVICE_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), DEVICE_TYPE, DeviceClass)) typedef struct _Device Device; typedef struct _DeviceClass DeviceClass; typedef struct _DevicePrivate DevicePrivate; struct _Device { GObject parent_instance; /*< private >*/ DevicePrivate *priv; }; struct _DeviceClass { GObjectClass parent_class; }; /* used by DEVICE_TYPE */ GType device_get_type(void) G_GNUC_CONST; /* * Constructor */ Device *device_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *device_get_dbus_object_path(Device *self); void device_cancel_pairing(Device *self, GError **error); void device_connect(Device *self, GError **error); void device_connect_profile(Device *self, const gchar *uuid, GError **error); void device_disconnect(Device *self, GError **error); void device_disconnect_profile(Device *self, const gchar *uuid, GError **error); void device_pair(Device *self, GError **error); void device_pair_async(Device *self, GAsyncReadyCallback callback, gpointer user_data); void device_pair_finish(Device *self, GAsyncResult *res, GError **error); GVariant *device_get_properties(Device *self, GError **error); void device_set_property(Device *self, const gchar *name, const GVariant *value, GError **error); const gchar *device_get_adapter(Device *self, GError **error); const gchar *device_get_address(Device *self, GError **error); const gchar *device_get_alias(Device *self, GError **error); void device_set_alias(Device *self, const gchar *value, GError **error); guint16 device_get_appearance(Device *self, GError **error); gboolean device_get_blocked(Device *self, GError **error); void device_set_blocked(Device *self, const gboolean value, GError **error); guint32 device_get_class(Device *self, GError **error); gboolean device_get_connected(Device *self, GError **error); const gchar *device_get_icon(Device *self, GError **error); gboolean device_get_legacy_pairing(Device *self, GError **error); const gchar *device_get_modalias(Device *self, GError **error); const gchar *device_get_name(Device *self, GError **error); gboolean device_get_paired(Device *self, GError **error); gint16 device_get_rssi(Device *self, GError **error); gboolean device_get_trusted(Device *self, GError **error); void device_set_trusted(Device *self, const gboolean value, GError **error); const gchar **device_get_uuids(Device *self, GError **error); #ifdef __cplusplus } #endif #endif /* __DEVICE_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/health_channel.c000066400000000000000000000171321315563672100236730ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "health_channel.h" #define HEALTH_CHANNEL_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), HEALTH_CHANNEL_TYPE, HealthChannelPrivate)) struct _HealthChannelPrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(HealthChannel, health_channel, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _health_channel_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _health_channel_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _health_channel_create_gdbus_proxy(HealthChannel *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void health_channel_dispose(GObject *gobject) { HealthChannel *self = HEALTH_CHANNEL(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(health_channel_parent_class)->dispose(gobject); } static void health_channel_finalize (GObject *gobject) { HealthChannel *self = HEALTH_CHANNEL(gobject); G_OBJECT_CLASS(health_channel_parent_class)->finalize(gobject); } static void health_channel_class_init(HealthChannelClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = health_channel_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _health_channel_get_property; gobject_class->set_property = _health_channel_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "HealthChannel D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void health_channel_init(HealthChannel *self) { self->priv = health_channel_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _health_channel_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { HealthChannel *self = HEALTH_CHANNEL(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, health_channel_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _health_channel_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { HealthChannel *self = HEALTH_CHANNEL(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _health_channel_create_gdbus_proxy(self, HEALTH_CHANNEL_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ HealthChannel *health_channel_new(const gchar *dbus_object_path) { return g_object_new(HEALTH_CHANNEL_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _health_channel_create_gdbus_proxy(HealthChannel *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(HEALTH_CHANNEL_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, HEALTH_CHANNEL_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "system", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *health_channel_get_dbus_object_path(HealthChannel *self) { g_assert(HEALTH_CHANNEL_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* fd Acquire() */ guint32 health_channel_acquire(HealthChannel *self, GError **error) { g_assert(HEALTH_CHANNEL_IS(self)); guint32 ret = 0; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "Acquire", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return 0; proxy_ret = g_variant_get_child_value(proxy_ret, 0); ret = g_variant_get_uint32(proxy_ret); g_variant_unref(proxy_ret); return ret; } /* void Release() */ void health_channel_release(HealthChannel *self, GError **error) { g_assert(HEALTH_CHANNEL_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Release", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* Properties access methods */ GVariant *health_channel_get_properties(HealthChannel *self, GError **error) { g_assert(HEALTH_CHANNEL_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, HEALTH_CHANNEL_DBUS_INTERFACE, error); } void health_channel_set_property(HealthChannel *self, const gchar *name, const GVariant *value, GError **error) { g_assert(HEALTH_CHANNEL_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, HEALTH_CHANNEL_DBUS_INTERFACE, name, value, error); } const gchar *health_channel_get_application(HealthChannel *self, GError **error) { g_assert(HEALTH_CHANNEL_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, HEALTH_CHANNEL_DBUS_INTERFACE, "Application", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *health_channel_get_device(HealthChannel *self, GError **error) { g_assert(HEALTH_CHANNEL_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, HEALTH_CHANNEL_DBUS_INTERFACE, "Device", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *health_channel_get_channel_type(HealthChannel *self, GError **error) { g_assert(HEALTH_CHANNEL_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, HEALTH_CHANNEL_DBUS_INTERFACE, "Type", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/health_channel.h000066400000000000000000000057241315563672100237040ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __HEALTH_CHANNEL_H #define __HEALTH_CHANNEL_H #ifdef __cplusplus extern "C" { #endif #include #define HEALTH_CHANNEL_DBUS_SERVICE "org.bluez" #define HEALTH_CHANNEL_DBUS_INTERFACE "org.bluez.HealthChannel1" /* * Type macros */ #define HEALTH_CHANNEL_TYPE (health_channel_get_type()) #define HEALTH_CHANNEL(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), HEALTH_CHANNEL_TYPE, HealthChannel)) #define HEALTH_CHANNEL_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), HEALTH_CHANNEL_TYPE)) #define HEALTH_CHANNEL_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), HEALTH_CHANNEL_TYPE, HealthChannelClass)) #define HEALTH_CHANNEL_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), HEALTH_CHANNEL_TYPE)) #define HEALTH_CHANNEL_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), HEALTH_CHANNEL_TYPE, HealthChannelClass)) typedef struct _HealthChannel HealthChannel; typedef struct _HealthChannelClass HealthChannelClass; typedef struct _HealthChannelPrivate HealthChannelPrivate; struct _HealthChannel { GObject parent_instance; /*< private >*/ HealthChannelPrivate *priv; }; struct _HealthChannelClass { GObjectClass parent_class; }; /* used by HEALTH_CHANNEL_TYPE */ GType health_channel_get_type(void) G_GNUC_CONST; /* * Constructor */ HealthChannel *health_channel_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *health_channel_get_dbus_object_path(HealthChannel *self); guint32 health_channel_acquire(HealthChannel *self, GError **error); void health_channel_release(HealthChannel *self, GError **error); GVariant *health_channel_get_properties(HealthChannel *self, GError **error); void health_channel_set_property(HealthChannel *self, const gchar *name, const GVariant *value, GError **error); const gchar *health_channel_get_application(HealthChannel *self, GError **error); const gchar *health_channel_get_device(HealthChannel *self, GError **error); // This has been renamed because 'health_channel_get_type' is already used by GLib const gchar *health_channel_get_channel_type(HealthChannel *self, GError **error); #ifdef __cplusplus } #endif #endif /* __HEALTH_CHANNEL_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/health_device.c000066400000000000000000000167251315563672100235310ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "health_device.h" #define HEALTH_DEVICE_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), HEALTH_DEVICE_TYPE, HealthDevicePrivate)) struct _HealthDevicePrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(HealthDevice, health_device, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _health_device_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _health_device_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _health_device_create_gdbus_proxy(HealthDevice *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void health_device_dispose(GObject *gobject) { HealthDevice *self = HEALTH_DEVICE(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(health_device_parent_class)->dispose(gobject); } static void health_device_finalize (GObject *gobject) { HealthDevice *self = HEALTH_DEVICE(gobject); G_OBJECT_CLASS(health_device_parent_class)->finalize(gobject); } static void health_device_class_init(HealthDeviceClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = health_device_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _health_device_get_property; gobject_class->set_property = _health_device_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "HealthDevice D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void health_device_init(HealthDevice *self) { self->priv = health_device_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _health_device_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { HealthDevice *self = HEALTH_DEVICE(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, health_device_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _health_device_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { HealthDevice *self = HEALTH_DEVICE(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _health_device_create_gdbus_proxy(self, HEALTH_DEVICE_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ HealthDevice *health_device_new(const gchar *dbus_object_path) { return g_object_new(HEALTH_DEVICE_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _health_device_create_gdbus_proxy(HealthDevice *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(HEALTH_DEVICE_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, HEALTH_DEVICE_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "system", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *health_device_get_dbus_object_path(HealthDevice *self) { g_assert(HEALTH_DEVICE_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* object CreateChannel(object application, string configuration) */ const gchar *health_device_create_channel(HealthDevice *self, const gchar *application, const gchar *configuration, GError **error) { g_assert(HEALTH_DEVICE_IS(self)); const gchar *ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "CreateChannel", g_variant_new ("(os)", application, configuration), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return NULL; proxy_ret = g_variant_get_child_value(proxy_ret, 0); ret = g_variant_get_string(proxy_ret, NULL); g_variant_unref(proxy_ret); return ret; } /* void DestroyChannel(object channel) */ void health_device_destroy_channel(HealthDevice *self, const gchar *channel, GError **error) { g_assert(HEALTH_DEVICE_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "DestroyChannel", g_variant_new ("(o)", channel), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* boolean Echo() */ gboolean health_device_echo(HealthDevice *self, GError **error) { g_assert(HEALTH_DEVICE_IS(self)); gboolean ret = FALSE; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "Echo", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return FALSE; proxy_ret = g_variant_get_child_value(proxy_ret, 0); ret = g_variant_get_boolean(proxy_ret); g_variant_unref(proxy_ret); return ret; } /* Properties access methods */ GVariant *health_device_get_properties(HealthDevice *self, GError **error) { g_assert(HEALTH_DEVICE_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, HEALTH_DEVICE_DBUS_INTERFACE, error); } void health_device_set_property(HealthDevice *self, const gchar *name, const GVariant *value, GError **error) { g_assert(HEALTH_DEVICE_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, HEALTH_DEVICE_DBUS_INTERFACE, name, value, error); } const gchar *health_device_get_main_channel(HealthDevice *self, GError **error) { g_assert(HEALTH_DEVICE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, HEALTH_DEVICE_DBUS_INTERFACE, "MainChannel", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/health_device.h000066400000000000000000000055251315563672100235320ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __HEALTH_DEVICE_H #define __HEALTH_DEVICE_H #ifdef __cplusplus extern "C" { #endif #include #define HEALTH_DEVICE_DBUS_SERVICE "org.bluez" #define HEALTH_DEVICE_DBUS_INTERFACE "org.bluez.HealthDevice1" /* * Type macros */ #define HEALTH_DEVICE_TYPE (health_device_get_type()) #define HEALTH_DEVICE(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), HEALTH_DEVICE_TYPE, HealthDevice)) #define HEALTH_DEVICE_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), HEALTH_DEVICE_TYPE)) #define HEALTH_DEVICE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), HEALTH_DEVICE_TYPE, HealthDeviceClass)) #define HEALTH_DEVICE_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), HEALTH_DEVICE_TYPE)) #define HEALTH_DEVICE_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), HEALTH_DEVICE_TYPE, HealthDeviceClass)) typedef struct _HealthDevice HealthDevice; typedef struct _HealthDeviceClass HealthDeviceClass; typedef struct _HealthDevicePrivate HealthDevicePrivate; struct _HealthDevice { GObject parent_instance; /*< private >*/ HealthDevicePrivate *priv; }; struct _HealthDeviceClass { GObjectClass parent_class; }; /* used by HEALTH_DEVICE_TYPE */ GType health_device_get_type(void) G_GNUC_CONST; /* * Constructor */ HealthDevice *health_device_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *health_device_get_dbus_object_path(HealthDevice *self); const gchar *health_device_create_channel(HealthDevice *self, const gchar *application, const gchar *configuration, GError **error); void health_device_destroy_channel(HealthDevice *self, const gchar *channel, GError **error); gboolean health_device_echo(HealthDevice *self, GError **error); GVariant *health_device_get_properties(HealthDevice *self, GError **error); void health_device_set_property(HealthDevice *self, const gchar *name, const GVariant *value, GError **error); const gchar *health_device_get_main_channel(HealthDevice *self, GError **error); #ifdef __cplusplus } #endif #endif /* __HEALTH_DEVICE_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/health_manager.c000066400000000000000000000116211315563672100236720ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "health_manager.h" #define HEALTH_MANAGER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), HEALTH_MANAGER_TYPE, HealthManagerPrivate)) struct _HealthManagerPrivate { GDBusProxy *proxy; }; G_DEFINE_TYPE_WITH_PRIVATE(HealthManager, health_manager, G_TYPE_OBJECT); enum { PROP_0, }; static void _health_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _health_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _health_manager_create_gdbus_proxy(HealthManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void health_manager_dispose(GObject *gobject) { HealthManager *self = HEALTH_MANAGER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Chain up to the parent class */ G_OBJECT_CLASS(health_manager_parent_class)->dispose(gobject); } static void health_manager_finalize (GObject *gobject) { HealthManager *self = HEALTH_MANAGER(gobject); G_OBJECT_CLASS(health_manager_parent_class)->finalize(gobject); } static void health_manager_class_init(HealthManagerClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = health_manager_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _health_manager_get_property; gobject_class->set_property = _health_manager_set_property; if (pspec) g_param_spec_unref(pspec); } static void health_manager_init(HealthManager *self) { self->priv = health_manager_get_instance_private (self); self->priv->proxy = NULL; g_assert(system_conn != NULL); GError *error = NULL; _health_manager_create_gdbus_proxy(self, HEALTH_MANAGER_DBUS_SERVICE, HEALTH_MANAGER_DBUS_PATH, &error); g_assert(error == NULL); } static void _health_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { HealthManager *self = HEALTH_MANAGER(object); switch (property_id) { default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _health_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { HealthManager *self = HEALTH_MANAGER(object); GError *error = NULL; switch (property_id) { default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ HealthManager *health_manager_new() { return g_object_new(HEALTH_MANAGER_TYPE, NULL); } /* Private DBus proxy creation */ static void _health_manager_create_gdbus_proxy(HealthManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(HEALTH_MANAGER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, HEALTH_MANAGER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* object CreateApplication(dict config) */ const gchar *health_manager_create_application(HealthManager *self, const GVariant *config, GError **error) { g_assert(HEALTH_MANAGER_IS(self)); const gchar *ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "CreateApplication", g_variant_new ("(@a{sv})", config), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return NULL; proxy_ret = g_variant_get_child_value(proxy_ret, 0); ret = g_variant_get_string(proxy_ret, NULL); g_variant_unref(proxy_ret); return ret; } /* void DestroyApplication(object application) */ void health_manager_destroy_application(HealthManager *self, const gchar *application, GError **error) { g_assert(HEALTH_MANAGER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "DestroyApplication", g_variant_new ("(o)", application), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/health_manager.h000066400000000000000000000047461315563672100237110ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __HEALTH_MANAGER_H #define __HEALTH_MANAGER_H #ifdef __cplusplus extern "C" { #endif #include #define HEALTH_MANAGER_DBUS_SERVICE "org.bluez" #define HEALTH_MANAGER_DBUS_INTERFACE "org.bluez.HealthManager1" #define HEALTH_MANAGER_DBUS_PATH "/org/bluez/" /* * Type macros */ #define HEALTH_MANAGER_TYPE (health_manager_get_type()) #define HEALTH_MANAGER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), HEALTH_MANAGER_TYPE, HealthManager)) #define HEALTH_MANAGER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), HEALTH_MANAGER_TYPE)) #define HEALTH_MANAGER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), HEALTH_MANAGER_TYPE, HealthManagerClass)) #define HEALTH_MANAGER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), HEALTH_MANAGER_TYPE)) #define HEALTH_MANAGER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), HEALTH_MANAGER_TYPE, HealthManagerClass)) typedef struct _HealthManager HealthManager; typedef struct _HealthManagerClass HealthManagerClass; typedef struct _HealthManagerPrivate HealthManagerPrivate; struct _HealthManager { GObject parent_instance; /*< private >*/ HealthManagerPrivate *priv; }; struct _HealthManagerClass { GObjectClass parent_class; }; /* used by HEALTH_MANAGER_TYPE */ GType health_manager_get_type(void) G_GNUC_CONST; /* * Constructor */ HealthManager *health_manager_new(); /* * Method definitions */ const gchar *health_manager_create_application(HealthManager *self, const GVariant *config, GError **error); void health_manager_destroy_application(HealthManager *self, const gchar *application, GError **error); #ifdef __cplusplus } #endif #endif /* __HEALTH_MANAGER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/heart_rate.c000066400000000000000000000136741315563672100230630ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "heart_rate.h" #define HEART_RATE_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), HEART_RATE_TYPE, HeartRatePrivate)) struct _HeartRatePrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(HeartRate, heart_rate, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _heart_rate_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _heart_rate_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _heart_rate_create_gdbus_proxy(HeartRate *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void heart_rate_dispose(GObject *gobject) { HeartRate *self = HEART_RATE(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(heart_rate_parent_class)->dispose(gobject); } static void heart_rate_finalize (GObject *gobject) { HeartRate *self = HEART_RATE(gobject); G_OBJECT_CLASS(heart_rate_parent_class)->finalize(gobject); } static void heart_rate_class_init(HeartRateClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = heart_rate_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _heart_rate_get_property; gobject_class->set_property = _heart_rate_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "HeartRate D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void heart_rate_init(HeartRate *self) { self->priv = heart_rate_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _heart_rate_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { HeartRate *self = HEART_RATE(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, heart_rate_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _heart_rate_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { HeartRate *self = HEART_RATE(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _heart_rate_create_gdbus_proxy(self, HEART_RATE_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ HeartRate *heart_rate_new(const gchar *dbus_object_path) { return g_object_new(HEART_RATE_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _heart_rate_create_gdbus_proxy(HeartRate *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(HEART_RATE_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, HEART_RATE_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "system", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *heart_rate_get_dbus_object_path(HeartRate *self) { g_assert(HEART_RATE_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* Properties access methods */ GVariant *heart_rate_get_properties(HeartRate *self, GError **error) { g_assert(HEART_RATE_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, HEART_RATE_DBUS_INTERFACE, error); } void heart_rate_set_property(HeartRate *self, const gchar *name, const GVariant *value, GError **error) { g_assert(HEART_RATE_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, HEART_RATE_DBUS_INTERFACE, name, value, error); } gboolean heart_rate_get_reset_supported(HeartRate *self, GError **error) { g_assert(HEART_RATE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, HEART_RATE_DBUS_INTERFACE, "ResetSupported", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/heart_rate.h000066400000000000000000000046611315563672100230640ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __HEART_RATE_H #define __HEART_RATE_H #ifdef __cplusplus extern "C" { #endif #include #define HEART_RATE_DBUS_SERVICE "org.bluez" #define HEART_RATE_DBUS_INTERFACE "org.bluez.HeartRate1" /* * Type macros */ #define HEART_RATE_TYPE (heart_rate_get_type()) #define HEART_RATE(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), HEART_RATE_TYPE, HeartRate)) #define HEART_RATE_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), HEART_RATE_TYPE)) #define HEART_RATE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), HEART_RATE_TYPE, HeartRateClass)) #define HEART_RATE_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), HEART_RATE_TYPE)) #define HEART_RATE_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), HEART_RATE_TYPE, HeartRateClass)) typedef struct _HeartRate HeartRate; typedef struct _HeartRateClass HeartRateClass; typedef struct _HeartRatePrivate HeartRatePrivate; struct _HeartRate { GObject parent_instance; /*< private >*/ HeartRatePrivate *priv; }; struct _HeartRateClass { GObjectClass parent_class; }; /* used by HEART_RATE_TYPE */ GType heart_rate_get_type(void) G_GNUC_CONST; /* * Constructor */ HeartRate *heart_rate_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *heart_rate_get_dbus_object_path(HeartRate *self); GVariant *heart_rate_get_properties(HeartRate *self, GError **error); void heart_rate_set_property(HeartRate *self, const gchar *name, const GVariant *value, GError **error); gboolean heart_rate_get_reset_supported(HeartRate *self, GError **error); #ifdef __cplusplus } #endif #endif /* __HEART_RATE_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/heart_rate_manager.c000066400000000000000000000121111315563672100245360ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "heart_rate_manager.h" #define HEART_RATE_MANAGER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), HEART_RATE_MANAGER_TYPE, HeartRateManagerPrivate)) struct _HeartRateManagerPrivate { GDBusProxy *proxy; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(HeartRateManager, heart_rate_manager, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _heart_rate_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _heart_rate_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _heart_rate_manager_create_gdbus_proxy(HeartRateManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void heart_rate_manager_dispose(GObject *gobject) { HeartRateManager *self = HEART_RATE_MANAGER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(heart_rate_manager_parent_class)->dispose(gobject); } static void heart_rate_manager_finalize (GObject *gobject) { HeartRateManager *self = HEART_RATE_MANAGER(gobject); G_OBJECT_CLASS(heart_rate_manager_parent_class)->finalize(gobject); } static void heart_rate_manager_class_init(HeartRateManagerClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = heart_rate_manager_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _heart_rate_manager_get_property; gobject_class->set_property = _heart_rate_manager_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "HeartRateManager D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void heart_rate_manager_init(HeartRateManager *self) { self->priv = heart_rate_manager_get_instance_private (self); self->priv->proxy = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _heart_rate_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { HeartRateManager *self = HEART_RATE_MANAGER(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, heart_rate_manager_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _heart_rate_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { HeartRateManager *self = HEART_RATE_MANAGER(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _heart_rate_manager_create_gdbus_proxy(self, HEART_RATE_MANAGER_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ HeartRateManager *heart_rate_manager_new(const gchar *dbus_object_path) { return g_object_new(HEART_RATE_MANAGER_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _heart_rate_manager_create_gdbus_proxy(HeartRateManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(HEART_RATE_MANAGER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, HEART_RATE_MANAGER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* Get DBus object path */ const gchar *heart_rate_manager_get_dbus_object_path(HeartRateManager *self) { g_assert(HEART_RATE_MANAGER_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/heart_rate_manager.h000066400000000000000000000046511315563672100245550ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __HEART_RATE_MANAGER_H #define __HEART_RATE_MANAGER_H #ifdef __cplusplus extern "C" { #endif #include #define HEART_RATE_MANAGER_DBUS_SERVICE "org.bluez" #define HEART_RATE_MANAGER_DBUS_INTERFACE "org.bluez.HeartRateManager1" /* * Type macros */ #define HEART_RATE_MANAGER_TYPE (heart_rate_manager_get_type()) #define HEART_RATE_MANAGER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), HEART_RATE_MANAGER_TYPE, HeartRateManager)) #define HEART_RATE_MANAGER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), HEART_RATE_MANAGER_TYPE)) #define HEART_RATE_MANAGER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), HEART_RATE_MANAGER_TYPE, HeartRateManagerClass)) #define HEART_RATE_MANAGER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), HEART_RATE_MANAGER_TYPE)) #define HEART_RATE_MANAGER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), HEART_RATE_MANAGER_TYPE, HeartRateManagerClass)) typedef struct _HeartRateManager HeartRateManager; typedef struct _HeartRateManagerClass HeartRateManagerClass; typedef struct _HeartRateManagerPrivate HeartRateManagerPrivate; struct _HeartRateManager { GObject parent_instance; /*< private >*/ HeartRateManagerPrivate *priv; }; struct _HeartRateManagerClass { GObjectClass parent_class; }; /* used by HEART_RATE_MANAGER_TYPE */ GType heart_rate_manager_get_type(void) G_GNUC_CONST; /* * Constructor */ HeartRateManager *heart_rate_manager_new(const gchar *dbus_object_path); const gchar *heart_rate_manager_get_dbus_object_path(HeartRateManager *self); #ifdef __cplusplus } #endif #endif /* __HEART_RATE_MANAGER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/media.c000066400000000000000000000134241315563672100220150ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "media.h" #define MEDIA_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), MEDIA_TYPE, MediaPrivate)) struct _MediaPrivate { GDBusProxy *proxy; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(Media, media, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _media_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _media_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _media_create_gdbus_proxy(Media *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void media_dispose(GObject *gobject) { Media *self = MEDIA(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(media_parent_class)->dispose(gobject); } static void media_finalize (GObject *gobject) { Media *self = MEDIA(gobject); G_OBJECT_CLASS(media_parent_class)->finalize(gobject); } static void media_class_init(MediaClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = media_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _media_get_property; gobject_class->set_property = _media_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "Media D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void media_init(Media *self) { self->priv = media_get_instance_private (self); self->priv->proxy = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _media_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { Media *self = MEDIA(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, media_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _media_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { Media *self = MEDIA(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _media_create_gdbus_proxy(self, MEDIA_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ Media *media_new(const gchar *dbus_object_path) { return g_object_new(MEDIA_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _media_create_gdbus_proxy(Media *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(MEDIA_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, MEDIA_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* Get DBus object path */ const gchar *media_get_dbus_object_path(Media *self) { g_assert(MEDIA_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* void RegisterEndpoint(object endpoint, dict properties) */ void media_register_endpoint(Media *self, const gchar *endpoint, const GVariant *properties, GError **error) { g_assert(MEDIA_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "RegisterEndpoint", g_variant_new ("(o@a{sv})", endpoint, properties), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void RegisterPlayer(object player, dict properties) */ void media_register_player(Media *self, const gchar *player, const GVariant *properties, GError **error) { g_assert(MEDIA_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "RegisterPlayer", g_variant_new ("(o@a{sv})", player, properties), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void UnregisterEndpoint(object endpoint) */ void media_unregister_endpoint(Media *self, const gchar *endpoint, GError **error) { g_assert(MEDIA_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "UnregisterEndpoint", g_variant_new ("(o)", endpoint), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void UnregisterPlayer(object player) */ void media_unregister_player(Media *self, const gchar *player, GError **error) { g_assert(MEDIA_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "UnregisterPlayer", g_variant_new ("(o)", player), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/media.h000066400000000000000000000046161315563672100220250ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __MEDIA_H #define __MEDIA_H #ifdef __cplusplus extern "C" { #endif #include #define MEDIA_DBUS_SERVICE "org.bluez" #define MEDIA_DBUS_INTERFACE "org.bluez.Media1" /* * Type macros */ #define MEDIA_TYPE (media_get_type()) #define MEDIA(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), MEDIA_TYPE, Media)) #define MEDIA_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), MEDIA_TYPE)) #define MEDIA_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), MEDIA_TYPE, MediaClass)) #define MEDIA_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), MEDIA_TYPE)) #define MEDIA_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), MEDIA_TYPE, MediaClass)) typedef struct _Media Media; typedef struct _MediaClass MediaClass; typedef struct _MediaPrivate MediaPrivate; struct _Media { GObject parent_instance; /*< private >*/ MediaPrivate *priv; }; struct _MediaClass { GObjectClass parent_class; }; /* used by MEDIA_TYPE */ GType media_get_type(void) G_GNUC_CONST; /* * Constructor */ Media *media_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *media_get_dbus_object_path(Media *self); void media_register_endpoint(Media *self, const gchar *endpoint, const GVariant *properties, GError **error); void media_register_player(Media *self, const gchar *player, const GVariant *properties, GError **error); void media_unregister_endpoint(Media *self, const gchar *endpoint, GError **error); void media_unregister_player(Media *self, const gchar *player, GError **error); #ifdef __cplusplus } #endif #endif /* __MEDIA_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/media_control.c000066400000000000000000000201141315563672100235470ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "media_control.h" #define MEDIA_CONTROL_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), MEDIA_CONTROL_TYPE, MediaControlPrivate)) struct _MediaControlPrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(MediaControl, media_control, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _media_control_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _media_control_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _media_control_create_gdbus_proxy(MediaControl *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void media_control_dispose(GObject *gobject) { MediaControl *self = MEDIA_CONTROL(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(media_control_parent_class)->dispose(gobject); } static void media_control_finalize (GObject *gobject) { MediaControl *self = MEDIA_CONTROL(gobject); G_OBJECT_CLASS(media_control_parent_class)->finalize(gobject); } static void media_control_class_init(MediaControlClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = media_control_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _media_control_get_property; gobject_class->set_property = _media_control_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "MediaControl D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void media_control_init(MediaControl *self) { self->priv = media_control_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _media_control_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { MediaControl *self = MEDIA_CONTROL(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, media_control_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _media_control_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { MediaControl *self = MEDIA_CONTROL(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _media_control_create_gdbus_proxy(self, MEDIA_CONTROL_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ MediaControl *media_control_new(const gchar *dbus_object_path) { return g_object_new(MEDIA_CONTROL_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _media_control_create_gdbus_proxy(MediaControl *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(MEDIA_CONTROL_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, MEDIA_CONTROL_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "system", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *media_control_get_dbus_object_path(MediaControl *self) { g_assert(MEDIA_CONTROL_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* void FastForward() */ void media_control_fast_forward(MediaControl *self, GError **error) { g_assert(MEDIA_CONTROL_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "FastForward", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Next() */ void media_control_next(MediaControl *self, GError **error) { g_assert(MEDIA_CONTROL_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Next", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Pause() */ void media_control_pause(MediaControl *self, GError **error) { g_assert(MEDIA_CONTROL_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Pause", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Play() */ void media_control_play(MediaControl *self, GError **error) { g_assert(MEDIA_CONTROL_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Play", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Previous() */ void media_control_previous(MediaControl *self, GError **error) { g_assert(MEDIA_CONTROL_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Previous", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Rewind() */ void media_control_rewind(MediaControl *self, GError **error) { g_assert(MEDIA_CONTROL_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Rewind", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Stop() */ void media_control_stop(MediaControl *self, GError **error) { g_assert(MEDIA_CONTROL_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Stop", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void VolumeDown() */ void media_control_volume_down(MediaControl *self, GError **error) { g_assert(MEDIA_CONTROL_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "VolumeDown", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void VolumeUp() */ void media_control_volume_up(MediaControl *self, GError **error) { g_assert(MEDIA_CONTROL_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "VolumeUp", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* Properties access methods */ GVariant *media_control_get_properties(MediaControl *self, GError **error) { g_assert(MEDIA_CONTROL_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, MEDIA_CONTROL_DBUS_INTERFACE, error); } void media_control_set_property(MediaControl *self, const gchar *name, const GVariant *value, GError **error) { g_assert(MEDIA_CONTROL_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, MEDIA_CONTROL_DBUS_INTERFACE, name, value, error); } gboolean media_control_get_connected(MediaControl *self, GError **error) { g_assert(MEDIA_CONTROL_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_CONTROL_DBUS_INTERFACE, "Connected", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/media_control.h000066400000000000000000000061521315563672100235620ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __MEDIA_CONTROL_H #define __MEDIA_CONTROL_H #ifdef __cplusplus extern "C" { #endif #include #define MEDIA_CONTROL_DBUS_SERVICE "org.bluez" #define MEDIA_CONTROL_DBUS_INTERFACE "org.bluez.MediaControl1" /* * Type macros */ #define MEDIA_CONTROL_TYPE (media_control_get_type()) #define MEDIA_CONTROL(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), MEDIA_CONTROL_TYPE, MediaControl)) #define MEDIA_CONTROL_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), MEDIA_CONTROL_TYPE)) #define MEDIA_CONTROL_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), MEDIA_CONTROL_TYPE, MediaControlClass)) #define MEDIA_CONTROL_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), MEDIA_CONTROL_TYPE)) #define MEDIA_CONTROL_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), MEDIA_CONTROL_TYPE, MediaControlClass)) typedef struct _MediaControl MediaControl; typedef struct _MediaControlClass MediaControlClass; typedef struct _MediaControlPrivate MediaControlPrivate; struct _MediaControl { GObject parent_instance; /*< private >*/ MediaControlPrivate *priv; }; struct _MediaControlClass { GObjectClass parent_class; }; /* used by MEDIA_CONTROL_TYPE */ GType media_control_get_type(void) G_GNUC_CONST; /* * Constructor */ MediaControl *media_control_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *media_control_get_dbus_object_path(MediaControl *self); void media_control_fast_forward(MediaControl *self, GError **error); void media_control_next(MediaControl *self, GError **error); void media_control_pause(MediaControl *self, GError **error); void media_control_play(MediaControl *self, GError **error); void media_control_previous(MediaControl *self, GError **error); void media_control_rewind(MediaControl *self, GError **error); void media_control_stop(MediaControl *self, GError **error); void media_control_volume_down(MediaControl *self, GError **error); void media_control_volume_up(MediaControl *self, GError **error); GVariant *media_control_get_properties(MediaControl *self, GError **error); void media_control_set_property(MediaControl *self, const gchar *name, const GVariant *value, GError **error); gboolean media_control_get_connected(MediaControl *self, GError **error); #ifdef __cplusplus } #endif #endif /* __MEDIA_CONTROL_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/media_player.c000066400000000000000000000321401315563672100233650ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "media_player.h" #define MEDIA_PLAYER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), MEDIA_PLAYER_TYPE, MediaPlayerPrivate)) struct _MediaPlayerPrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(MediaPlayer, media_player, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _media_player_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _media_player_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _media_player_create_gdbus_proxy(MediaPlayer *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void media_player_dispose(GObject *gobject) { MediaPlayer *self = MEDIA_PLAYER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(media_player_parent_class)->dispose(gobject); } static void media_player_finalize (GObject *gobject) { MediaPlayer *self = MEDIA_PLAYER(gobject); G_OBJECT_CLASS(media_player_parent_class)->finalize(gobject); } static void media_player_class_init(MediaPlayerClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = media_player_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _media_player_get_property; gobject_class->set_property = _media_player_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "MediaPlayer D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void media_player_init(MediaPlayer *self) { self->priv = media_player_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _media_player_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { MediaPlayer *self = MEDIA_PLAYER(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, media_player_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _media_player_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { MediaPlayer *self = MEDIA_PLAYER(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _media_player_create_gdbus_proxy(self, MEDIA_PLAYER_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ MediaPlayer *media_player_new(const gchar *dbus_object_path) { return g_object_new(MEDIA_PLAYER_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _media_player_create_gdbus_proxy(MediaPlayer *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, MEDIA_PLAYER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "system", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *media_player_get_dbus_object_path(MediaPlayer *self) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* void FastForward() */ void media_player_fast_forward(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "FastForward", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Next() */ void media_player_next(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Next", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Pause() */ void media_player_pause(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Pause", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Play() */ void media_player_play(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Play", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Previous() */ void media_player_previous(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Previous", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Rewind() */ void media_player_rewind(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Rewind", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Stop() */ void media_player_stop(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Stop", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* Properties access methods */ GVariant *media_player_get_properties(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, error); } void media_player_set_property(MediaPlayer *self, const gchar *name, const GVariant *value, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, name, value, error); } gboolean media_player_get_browsable(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Browsable", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } const gchar *media_player_get_device(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Device", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *media_player_get_equalizer(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Equalizer", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } void media_player_set_equalizer(MediaPlayer *self, const gchar *value, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Equalizer", g_variant_new_string(value), error); } const gchar *media_player_get_name(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Name", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } guint32 media_player_get_position(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Position", error); if(prop == NULL) return 0; guint32 ret = g_variant_get_uint32(prop); g_variant_unref(prop); return ret; } const gchar *media_player_get_repeat(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Repeat", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } void media_player_set_repeat(MediaPlayer *self, const gchar *value, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Repeat", g_variant_new_string(value), error); } const gchar *media_player_get_scan(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Scan", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } void media_player_set_scan(MediaPlayer *self, const gchar *value, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Scan", g_variant_new_string(value), error); } gboolean media_player_get_searchable(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Searchable", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } const gchar *media_player_get_shuffle(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Shuffle", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } void media_player_set_shuffle(MediaPlayer *self, const gchar *value, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Shuffle", g_variant_new_string(value), error); } const gchar *media_player_get_status(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Status", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *media_player_get_subtype(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Subtype", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } GVariant *media_player_get_track(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Track", error); if(prop == NULL) return NULL; GVariant *ret = g_variant_ref_sink(prop); g_variant_unref(prop); return ret; } const gchar *media_player_get_player_type(MediaPlayer *self, GError **error) { g_assert(MEDIA_PLAYER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, MEDIA_PLAYER_DBUS_INTERFACE, "Type", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/media_player.h000066400000000000000000000102761315563672100234000ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __MEDIA_PLAYER_H #define __MEDIA_PLAYER_H #ifdef __cplusplus extern "C" { #endif #include #define MEDIA_PLAYER_DBUS_SERVICE "org.bluez" #define MEDIA_PLAYER_DBUS_INTERFACE "org.bluez.MediaPlayer1" /* * Type macros */ #define MEDIA_PLAYER_TYPE (media_player_get_type()) #define MEDIA_PLAYER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), MEDIA_PLAYER_TYPE, MediaPlayer)) #define MEDIA_PLAYER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), MEDIA_PLAYER_TYPE)) #define MEDIA_PLAYER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), MEDIA_PLAYER_TYPE, MediaPlayerClass)) #define MEDIA_PLAYER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), MEDIA_PLAYER_TYPE)) #define MEDIA_PLAYER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), MEDIA_PLAYER_TYPE, MediaPlayerClass)) typedef struct _MediaPlayer MediaPlayer; typedef struct _MediaPlayerClass MediaPlayerClass; typedef struct _MediaPlayerPrivate MediaPlayerPrivate; struct _MediaPlayer { GObject parent_instance; /*< private >*/ MediaPlayerPrivate *priv; }; struct _MediaPlayerClass { GObjectClass parent_class; }; /* used by MEDIA_PLAYER_TYPE */ GType media_player_get_type(void) G_GNUC_CONST; /* * Constructor */ MediaPlayer *media_player_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *media_player_get_dbus_object_path(MediaPlayer *self); void media_player_fast_forward(MediaPlayer *self, GError **error); void media_player_next(MediaPlayer *self, GError **error); void media_player_pause(MediaPlayer *self, GError **error); void media_player_play(MediaPlayer *self, GError **error); void media_player_previous(MediaPlayer *self, GError **error); void media_player_rewind(MediaPlayer *self, GError **error); void media_player_stop(MediaPlayer *self, GError **error); GVariant *media_player_get_properties(MediaPlayer *self, GError **error); void media_player_set_property(MediaPlayer *self, const gchar *name, const GVariant *value, GError **error); gboolean media_player_get_browsable(MediaPlayer *self, GError **error); const gchar *media_player_get_device(MediaPlayer *self, GError **error); const gchar *media_player_get_equalizer(MediaPlayer *self, GError **error); void media_player_set_equalizer(MediaPlayer *self, const gchar *value, GError **error); const gchar *media_player_get_name(MediaPlayer *self, GError **error); guint32 media_player_get_position(MediaPlayer *self, GError **error); const gchar *media_player_get_repeat(MediaPlayer *self, GError **error); void media_player_set_repeat(MediaPlayer *self, const gchar *value, GError **error); const gchar *media_player_get_scan(MediaPlayer *self, GError **error); void media_player_set_scan(MediaPlayer *self, const gchar *value, GError **error); gboolean media_player_get_searchable(MediaPlayer *self, GError **error); const gchar *media_player_get_shuffle(MediaPlayer *self, GError **error); void media_player_set_shuffle(MediaPlayer *self, const gchar *value, GError **error); const gchar *media_player_get_status(MediaPlayer *self, GError **error); const gchar *media_player_get_subtype(MediaPlayer *self, GError **error); GVariant *media_player_get_track(MediaPlayer *self, GError **error); // This has been renamed because 'media_player_get_type' is already used by GLib const gchar *media_player_get_player_type(MediaPlayer *self, GError **error); #ifdef __cplusplus } #endif #endif /* __MEDIA_PLAYER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/network.c000066400000000000000000000162661315563672100224360ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "network.h" #define NETWORK_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), NETWORK_TYPE, NetworkPrivate)) struct _NetworkPrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(Network, network, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _network_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _network_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _network_create_gdbus_proxy(Network *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void network_dispose(GObject *gobject) { Network *self = NETWORK(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(network_parent_class)->dispose(gobject); } static void network_finalize (GObject *gobject) { Network *self = NETWORK(gobject); G_OBJECT_CLASS(network_parent_class)->finalize(gobject); } static void network_class_init(NetworkClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = network_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _network_get_property; gobject_class->set_property = _network_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "Network D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void network_init(Network *self) { self->priv = network_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _network_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { Network *self = NETWORK(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, network_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _network_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { Network *self = NETWORK(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _network_create_gdbus_proxy(self, NETWORK_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ Network *network_new(const gchar *dbus_object_path) { return g_object_new(NETWORK_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _network_create_gdbus_proxy(Network *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(NETWORK_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, NETWORK_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "system", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *network_get_dbus_object_path(Network *self) { g_assert(NETWORK_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* string Connect(string uuid) */ const gchar *network_connect(Network *self, const gchar *uuid, GError **error) { g_assert(NETWORK_IS(self)); const gchar *ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "Connect", g_variant_new ("(s)", uuid), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return NULL; proxy_ret = g_variant_get_child_value(proxy_ret, 0); ret = g_variant_get_string(proxy_ret, NULL); g_variant_unref(proxy_ret); return ret; } /* void Disconnect() */ void network_disconnect(Network *self, GError **error) { g_assert(NETWORK_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Disconnect", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* Properties access methods */ GVariant *network_get_properties(Network *self, GError **error) { g_assert(NETWORK_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, NETWORK_DBUS_INTERFACE, error); } void network_set_property(Network *self, const gchar *name, const GVariant *value, GError **error) { g_assert(NETWORK_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, NETWORK_DBUS_INTERFACE, name, value, error); } gboolean network_get_connected(Network *self, GError **error) { g_assert(NETWORK_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, NETWORK_DBUS_INTERFACE, "Connected", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } const gchar *network_get_interface(Network *self, GError **error) { g_assert(NETWORK_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, NETWORK_DBUS_INTERFACE, "Interface", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *network_get_uuid(Network *self, GError **error) { g_assert(NETWORK_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, NETWORK_DBUS_INTERFACE, "UUID", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/network.h000066400000000000000000000051111315563672100224260ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __NETWORK_H #define __NETWORK_H #ifdef __cplusplus extern "C" { #endif #include #define NETWORK_DBUS_SERVICE "org.bluez" #define NETWORK_DBUS_INTERFACE "org.bluez.Network1" /* * Type macros */ #define NETWORK_TYPE (network_get_type()) #define NETWORK(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), NETWORK_TYPE, Network)) #define NETWORK_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), NETWORK_TYPE)) #define NETWORK_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), NETWORK_TYPE, NetworkClass)) #define NETWORK_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), NETWORK_TYPE)) #define NETWORK_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), NETWORK_TYPE, NetworkClass)) typedef struct _Network Network; typedef struct _NetworkClass NetworkClass; typedef struct _NetworkPrivate NetworkPrivate; struct _Network { GObject parent_instance; /*< private >*/ NetworkPrivate *priv; }; struct _NetworkClass { GObjectClass parent_class; }; /* used by NETWORK_TYPE */ GType network_get_type(void) G_GNUC_CONST; /* * Constructor */ Network *network_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *network_get_dbus_object_path(Network *self); const gchar *network_connect(Network *self, const gchar *uuid, GError **error); void network_disconnect(Network *self, GError **error); GVariant *network_get_properties(Network *self, GError **error); void network_set_property(Network *self, const gchar *name, const GVariant *value, GError **error); gboolean network_get_connected(Network *self, GError **error); const gchar *network_get_interface(Network *self, GError **error); const gchar *network_get_uuid(Network *self, GError **error); #ifdef __cplusplus } #endif #endif /* __NETWORK_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/network_server.c000066400000000000000000000130101315563672100240040ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "network_server.h" #define NETWORK_SERVER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), NETWORK_SERVER_TYPE, NetworkServerPrivate)) struct _NetworkServerPrivate { GDBusProxy *proxy; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(NetworkServer, network_server, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _network_server_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _network_server_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _network_server_create_gdbus_proxy(NetworkServer *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void network_server_dispose(GObject *gobject) { NetworkServer *self = NETWORK_SERVER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(network_server_parent_class)->dispose(gobject); } static void network_server_finalize (GObject *gobject) { NetworkServer *self = NETWORK_SERVER(gobject); G_OBJECT_CLASS(network_server_parent_class)->finalize(gobject); } static void network_server_class_init(NetworkServerClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = network_server_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _network_server_get_property; gobject_class->set_property = _network_server_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "NetworkServer D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void network_server_init(NetworkServer *self) { self->priv = network_server_get_instance_private (self); self->priv->proxy = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _network_server_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { NetworkServer *self = NETWORK_SERVER(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, network_server_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _network_server_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { NetworkServer *self = NETWORK_SERVER(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _network_server_create_gdbus_proxy(self, NETWORK_SERVER_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ NetworkServer *network_server_new(const gchar *dbus_object_path) { return g_object_new(NETWORK_SERVER_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _network_server_create_gdbus_proxy(NetworkServer *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(NETWORK_SERVER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, NETWORK_SERVER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* Get DBus object path */ const gchar *network_server_get_dbus_object_path(NetworkServer *self) { g_assert(NETWORK_SERVER_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* void Register(string uuid, string bridge) */ void network_server_register(NetworkServer *self, const gchar *uuid, const gchar *bridge, GError **error) { g_assert(NETWORK_SERVER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Register", g_variant_new ("(ss)", uuid, bridge), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Unregister(string uuid) */ void network_server_unregister(NetworkServer *self, const gchar *uuid, GError **error) { g_assert(NETWORK_SERVER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Unregister", g_variant_new ("(s)", uuid), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/network_server.h000066400000000000000000000050121315563672100240140ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __NETWORK_SERVER_H #define __NETWORK_SERVER_H #ifdef __cplusplus extern "C" { #endif #include #define NETWORK_SERVER_DBUS_SERVICE "org.bluez" #define NETWORK_SERVER_DBUS_INTERFACE "org.bluez.NetworkServer1" /* * Type macros */ #define NETWORK_SERVER_TYPE (network_server_get_type()) #define NETWORK_SERVER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), NETWORK_SERVER_TYPE, NetworkServer)) #define NETWORK_SERVER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), NETWORK_SERVER_TYPE)) #define NETWORK_SERVER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), NETWORK_SERVER_TYPE, NetworkServerClass)) #define NETWORK_SERVER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), NETWORK_SERVER_TYPE)) #define NETWORK_SERVER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), NETWORK_SERVER_TYPE, NetworkServerClass)) typedef struct _NetworkServer NetworkServer; typedef struct _NetworkServerClass NetworkServerClass; typedef struct _NetworkServerPrivate NetworkServerPrivate; struct _NetworkServer { GObject parent_instance; /*< private >*/ NetworkServerPrivate *priv; }; struct _NetworkServerClass { GObjectClass parent_class; }; /* used by NETWORK_SERVER_TYPE */ GType network_server_get_type(void) G_GNUC_CONST; /* * Constructor */ NetworkServer *network_server_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *network_server_get_dbus_object_path(NetworkServer *self); void network_server_register(NetworkServer *self, const gchar *uuid, const gchar *bridge, GError **error); void network_server_unregister(NetworkServer *self, const gchar *uuid, GError **error); #ifdef __cplusplus } #endif #endif /* __NETWORK_SERVER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/000077500000000000000000000000001315563672100215235ustar00rootroot00000000000000bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_agent_manager.c000066400000000000000000000114601315563672100254760ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../../dbus-common.h" #include "../../properties.h" #include "obex_agent_manager.h" #define OBEX_AGENT_MANAGER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), OBEX_AGENT_MANAGER_TYPE, ObexAgentManagerPrivate)) struct _ObexAgentManagerPrivate { GDBusProxy *proxy; }; G_DEFINE_TYPE_WITH_PRIVATE(ObexAgentManager, obex_agent_manager, G_TYPE_OBJECT); enum { PROP_0, }; static void _obex_agent_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _obex_agent_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _obex_agent_manager_create_gdbus_proxy(ObexAgentManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void obex_agent_manager_dispose(GObject *gobject) { ObexAgentManager *self = OBEX_AGENT_MANAGER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Chain up to the parent class */ G_OBJECT_CLASS(obex_agent_manager_parent_class)->dispose(gobject); } static void obex_agent_manager_finalize (GObject *gobject) { ObexAgentManager *self = OBEX_AGENT_MANAGER(gobject); G_OBJECT_CLASS(obex_agent_manager_parent_class)->finalize(gobject); } static void obex_agent_manager_class_init(ObexAgentManagerClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = obex_agent_manager_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _obex_agent_manager_get_property; gobject_class->set_property = _obex_agent_manager_set_property; if (pspec) g_param_spec_unref(pspec); } static void obex_agent_manager_init(ObexAgentManager *self) { self->priv = obex_agent_manager_get_instance_private (self); self->priv->proxy = NULL; g_assert(session_conn != NULL); GError *error = NULL; _obex_agent_manager_create_gdbus_proxy(self, OBEX_AGENT_MANAGER_DBUS_SERVICE, OBEX_AGENT_MANAGER_DBUS_PATH, &error); g_assert(error == NULL); } static void _obex_agent_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ObexAgentManager *self = OBEX_AGENT_MANAGER(object); switch (property_id) { default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _obex_agent_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ObexAgentManager *self = OBEX_AGENT_MANAGER(object); GError *error = NULL; switch (property_id) { default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ObexAgentManager *obex_agent_manager_new() { return g_object_new(OBEX_AGENT_MANAGER_TYPE, NULL); } /* Private DBus proxy creation */ static void _obex_agent_manager_create_gdbus_proxy(ObexAgentManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(OBEX_AGENT_MANAGER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(session_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, OBEX_AGENT_MANAGER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* void RegisterAgent(object agent) */ void obex_agent_manager_register_agent(ObexAgentManager *self, const gchar *agent, GError **error) { g_assert(OBEX_AGENT_MANAGER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "RegisterAgent", g_variant_new ("(o)", agent), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void UnregisterAgent(object agent) */ void obex_agent_manager_unregister_agent(ObexAgentManager *self, const gchar *agent, GError **error) { g_assert(OBEX_AGENT_MANAGER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "UnregisterAgent", g_variant_new ("(o)", agent), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_agent_manager.h000066400000000000000000000051431315563672100255040ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __OBEX_AGENT_MANAGER_H #define __OBEX_AGENT_MANAGER_H #ifdef __cplusplus extern "C" { #endif #include #define OBEX_AGENT_MANAGER_DBUS_SERVICE "org.bluez.obex" #define OBEX_AGENT_MANAGER_DBUS_INTERFACE "org.bluez.obex.AgentManager1" #define OBEX_AGENT_MANAGER_DBUS_PATH "/org/bluez/obex" /* * Type macros */ #define OBEX_AGENT_MANAGER_TYPE (obex_agent_manager_get_type()) #define OBEX_AGENT_MANAGER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), OBEX_AGENT_MANAGER_TYPE, ObexAgentManager)) #define OBEX_AGENT_MANAGER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), OBEX_AGENT_MANAGER_TYPE)) #define OBEX_AGENT_MANAGER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), OBEX_AGENT_MANAGER_TYPE, ObexAgentManagerClass)) #define OBEX_AGENT_MANAGER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), OBEX_AGENT_MANAGER_TYPE)) #define OBEX_AGENT_MANAGER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), OBEX_AGENT_MANAGER_TYPE, ObexAgentManagerClass)) typedef struct _ObexAgentManager ObexAgentManager; typedef struct _ObexAgentManagerClass ObexAgentManagerClass; typedef struct _ObexAgentManagerPrivate ObexAgentManagerPrivate; struct _ObexAgentManager { GObject parent_instance; /*< private >*/ ObexAgentManagerPrivate *priv; }; struct _ObexAgentManagerClass { GObjectClass parent_class; }; /* used by OBEX_AGENT_MANAGER_TYPE */ GType obex_agent_manager_get_type(void) G_GNUC_CONST; /* * Constructor */ ObexAgentManager *obex_agent_manager_new(); /* * Method definitions */ void obex_agent_manager_register_agent(ObexAgentManager *self, const gchar *agent, GError **error); void obex_agent_manager_unregister_agent(ObexAgentManager *self, const gchar *agent, GError **error); #ifdef __cplusplus } #endif #endif /* __OBEX_AGENT_MANAGER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_client.c000066400000000000000000000114251315563672100241650ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../../dbus-common.h" #include "../../properties.h" #include "obex_client.h" #define OBEX_CLIENT_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), OBEX_CLIENT_TYPE, ObexClientPrivate)) struct _ObexClientPrivate { GDBusProxy *proxy; }; G_DEFINE_TYPE_WITH_PRIVATE(ObexClient, obex_client, G_TYPE_OBJECT); enum { PROP_0, }; static void _obex_client_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _obex_client_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _obex_client_create_gdbus_proxy(ObexClient *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void obex_client_dispose(GObject *gobject) { ObexClient *self = OBEX_CLIENT(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Chain up to the parent class */ G_OBJECT_CLASS(obex_client_parent_class)->dispose(gobject); } static void obex_client_finalize (GObject *gobject) { ObexClient *self = OBEX_CLIENT(gobject); G_OBJECT_CLASS(obex_client_parent_class)->finalize(gobject); } static void obex_client_class_init(ObexClientClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = obex_client_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _obex_client_get_property; gobject_class->set_property = _obex_client_set_property; if (pspec) g_param_spec_unref(pspec); } static void obex_client_init(ObexClient *self) { self->priv = obex_client_get_instance_private (self); self->priv->proxy = NULL; g_assert(session_conn != NULL); GError *error = NULL; _obex_client_create_gdbus_proxy(self, OBEX_CLIENT_DBUS_SERVICE, OBEX_CLIENT_DBUS_PATH, &error); g_assert(error == NULL); } static void _obex_client_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ObexClient *self = OBEX_CLIENT(object); switch (property_id) { default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _obex_client_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ObexClient *self = OBEX_CLIENT(object); GError *error = NULL; switch (property_id) { default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ObexClient *obex_client_new() { return g_object_new(OBEX_CLIENT_TYPE, NULL); } /* Private DBus proxy creation */ static void _obex_client_create_gdbus_proxy(ObexClient *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(OBEX_CLIENT_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(session_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, OBEX_CLIENT_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* object CreateSession(string destination, dict args) */ const gchar *obex_client_create_session(ObexClient *self, const gchar *destination, const GVariant *args, GError **error) { g_assert(OBEX_CLIENT_IS(self)); const gchar *ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "CreateSession", g_variant_new ("(s@a{sv})", destination, args), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret == NULL) return NULL; proxy_ret = g_variant_get_child_value(proxy_ret, 0); ret = g_variant_get_string(proxy_ret, NULL); g_variant_unref(proxy_ret); return ret; } /* void RemoveSession(object session) */ void obex_client_remove_session(ObexClient *self, const gchar *session, GError **error) { g_assert(OBEX_CLIENT_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "RemoveSession", g_variant_new ("(o)", session), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_client.h000066400000000000000000000046061315563672100241750ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __OBEX_CLIENT_H #define __OBEX_CLIENT_H #ifdef __cplusplus extern "C" { #endif #include #define OBEX_CLIENT_DBUS_SERVICE "org.bluez.obex" #define OBEX_CLIENT_DBUS_INTERFACE "org.bluez.obex.Client1" #define OBEX_CLIENT_DBUS_PATH "/org/bluez/obex" /* * Type macros */ #define OBEX_CLIENT_TYPE (obex_client_get_type()) #define OBEX_CLIENT(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), OBEX_CLIENT_TYPE, ObexClient)) #define OBEX_CLIENT_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), OBEX_CLIENT_TYPE)) #define OBEX_CLIENT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), OBEX_CLIENT_TYPE, ObexClientClass)) #define OBEX_CLIENT_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), OBEX_CLIENT_TYPE)) #define OBEX_CLIENT_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), OBEX_CLIENT_TYPE, ObexClientClass)) typedef struct _ObexClient ObexClient; typedef struct _ObexClientClass ObexClientClass; typedef struct _ObexClientPrivate ObexClientPrivate; struct _ObexClient { GObject parent_instance; /*< private >*/ ObexClientPrivate *priv; }; struct _ObexClientClass { GObjectClass parent_class; }; /* used by OBEX_CLIENT_TYPE */ GType obex_client_get_type(void) G_GNUC_CONST; /* * Constructor */ ObexClient *obex_client_new(); /* * Method definitions */ const gchar *obex_client_create_session(ObexClient *self, const gchar *destination, const GVariant *args, GError **error); void obex_client_remove_session(ObexClient *self, const gchar *session, GError **error); #ifdef __cplusplus } #endif #endif /* __OBEX_CLIENT_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_file_transfer.c000066400000000000000000000203631315563672100255330ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../../dbus-common.h" #include "../../properties.h" #include "obex_file_transfer.h" #define OBEX_FILE_TRANSFER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), OBEX_FILE_TRANSFER_TYPE, ObexFileTransferPrivate)) struct _ObexFileTransferPrivate { GDBusProxy *proxy; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(ObexFileTransfer, obex_file_transfer, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _obex_file_transfer_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _obex_file_transfer_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _obex_file_transfer_create_gdbus_proxy(ObexFileTransfer *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void obex_file_transfer_dispose(GObject *gobject) { ObexFileTransfer *self = OBEX_FILE_TRANSFER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(obex_file_transfer_parent_class)->dispose(gobject); } static void obex_file_transfer_finalize (GObject *gobject) { ObexFileTransfer *self = OBEX_FILE_TRANSFER(gobject); G_OBJECT_CLASS(obex_file_transfer_parent_class)->finalize(gobject); } static void obex_file_transfer_class_init(ObexFileTransferClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = obex_file_transfer_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _obex_file_transfer_get_property; gobject_class->set_property = _obex_file_transfer_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "ObexFileTransfer D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void obex_file_transfer_init(ObexFileTransfer *self) { self->priv = obex_file_transfer_get_instance_private (self); self->priv->proxy = NULL; self->priv->object_path = NULL; g_assert(session_conn != NULL); } static void _obex_file_transfer_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ObexFileTransfer *self = OBEX_FILE_TRANSFER(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, obex_file_transfer_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _obex_file_transfer_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ObexFileTransfer *self = OBEX_FILE_TRANSFER(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _obex_file_transfer_create_gdbus_proxy(self, OBEX_FILE_TRANSFER_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ObexFileTransfer *obex_file_transfer_new(const gchar *dbus_object_path) { return g_object_new(OBEX_FILE_TRANSFER_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _obex_file_transfer_create_gdbus_proxy(ObexFileTransfer *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(OBEX_FILE_TRANSFER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(session_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, OBEX_FILE_TRANSFER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* Get DBus object path */ const gchar *obex_file_transfer_get_dbus_object_path(ObexFileTransfer *self) { g_assert(OBEX_FILE_TRANSFER_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* void ChangeFolder(string folder) */ void obex_file_transfer_change_folder(ObexFileTransfer *self, const gchar *folder, GError **error) { g_assert(OBEX_FILE_TRANSFER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "ChangeFolder", g_variant_new ("(s)", folder), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void CopyFile(string sourcefile, string targetfile) */ void obex_file_transfer_copy_file(ObexFileTransfer *self, const gchar *sourcefile, const gchar *targetfile, GError **error) { g_assert(OBEX_FILE_TRANSFER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "CopyFile", g_variant_new ("(ss)", sourcefile, targetfile), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void CreateFolder(string folder) */ void obex_file_transfer_create_folder(ObexFileTransfer *self, const gchar *folder, GError **error) { g_assert(OBEX_FILE_TRANSFER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "CreateFolder", g_variant_new ("(s)", folder), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Delete(string file) */ void obex_file_transfer_delete(ObexFileTransfer *self, const gchar *file, GError **error) { g_assert(OBEX_FILE_TRANSFER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Delete", g_variant_new ("(s)", file), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* object, dict GetFile(string targetfile, string sourcefile) */ GVariant *obex_file_transfer_get_file(ObexFileTransfer *self, const gchar *targetfile, const gchar *sourcefile, GError **error) { g_assert(OBEX_FILE_TRANSFER_IS(self)); GVariant *ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "GetFile", g_variant_new ("(ss)", targetfile, sourcefile), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return NULL; ret = g_variant_ref_sink(proxy_ret); g_variant_unref(proxy_ret); return ret; } /* array{dict} ListFolder() */ GVariant *obex_file_transfer_list_folder(ObexFileTransfer *self, GError **error) { g_assert(OBEX_FILE_TRANSFER_IS(self)); GVariant *ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "ListFolder", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return NULL; proxy_ret = g_variant_get_child_value(proxy_ret, 0); ret = g_variant_ref_sink(proxy_ret); g_variant_unref(proxy_ret); return ret; } /* void MoveFile(string sourcefile, string targetfile) */ void obex_file_transfer_move_file(ObexFileTransfer *self, const gchar *sourcefile, const gchar *targetfile, GError **error) { g_assert(OBEX_FILE_TRANSFER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "MoveFile", g_variant_new ("(ss)", sourcefile, targetfile), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* object, dict PutFile(string sourcefile, string targetfile) */ GVariant *obex_file_transfer_put_file(ObexFileTransfer *self, const gchar *sourcefile, const gchar *targetfile, GError **error) { g_assert(OBEX_FILE_TRANSFER_IS(self)); GVariant *ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "PutFile", g_variant_new ("(ss)", targetfile, sourcefile), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return NULL; ret = g_variant_ref_sink(proxy_ret); g_variant_unref(proxy_ret); return ret; }bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_file_transfer.h000066400000000000000000000064761315563672100255510ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __OBEX_FILE_TRANSFER_H #define __OBEX_FILE_TRANSFER_H #ifdef __cplusplus extern "C" { #endif #include #define OBEX_FILE_TRANSFER_DBUS_SERVICE "org.bluez.obex" #define OBEX_FILE_TRANSFER_DBUS_INTERFACE "org.bluez.obex.FileTransfer" /* * Type macros */ #define OBEX_FILE_TRANSFER_TYPE (obex_file_transfer_get_type()) #define OBEX_FILE_TRANSFER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), OBEX_FILE_TRANSFER_TYPE, ObexFileTransfer)) #define OBEX_FILE_TRANSFER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), OBEX_FILE_TRANSFER_TYPE)) #define OBEX_FILE_TRANSFER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), OBEX_FILE_TRANSFER_TYPE, ObexFileTransferClass)) #define OBEX_FILE_TRANSFER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), OBEX_FILE_TRANSFER_TYPE)) #define OBEX_FILE_TRANSFER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), OBEX_FILE_TRANSFER_TYPE, ObexFileTransferClass)) typedef struct _ObexFileTransfer ObexFileTransfer; typedef struct _ObexFileTransferClass ObexFileTransferClass; typedef struct _ObexFileTransferPrivate ObexFileTransferPrivate; struct _ObexFileTransfer { GObject parent_instance; /*< private >*/ ObexFileTransferPrivate *priv; }; struct _ObexFileTransferClass { GObjectClass parent_class; }; /* used by OBEX_FILE_TRANSFER_TYPE */ GType obex_file_transfer_get_type(void) G_GNUC_CONST; /* * Constructor */ ObexFileTransfer *obex_file_transfer_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *obex_file_transfer_get_dbus_object_path(ObexFileTransfer *self); void obex_file_transfer_change_folder(ObexFileTransfer *self, const gchar *folder, GError **error); void obex_file_transfer_copy_file(ObexFileTransfer *self, const gchar *sourcefile, const gchar *targetfile, GError **error); void obex_file_transfer_create_folder(ObexFileTransfer *self, const gchar *folder, GError **error); void obex_file_transfer_delete(ObexFileTransfer *self, const gchar *file, GError **error); GVariant *obex_file_transfer_get_file(ObexFileTransfer *self, const gchar *targetfile, const gchar *sourcefile, GError **error); GVariant *obex_file_transfer_list_folder(ObexFileTransfer *self, GError **error); void obex_file_transfer_move_file(ObexFileTransfer *self, const gchar *sourcefile, const gchar *targetfile, GError **error); GVariant *obex_file_transfer_put_file(ObexFileTransfer *self, const gchar *sourcefile, const gchar *targetfile, GError **error); #ifdef __cplusplus } #endif #endif /* __OBEX_FILE_TRANSFER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_message.c000066400000000000000000000275061315563672100243420ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../../dbus-common.h" #include "../../properties.h" #include "obex_message.h" #define OBEX_MESSAGE_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), OBEX_MESSAGE_TYPE, ObexMessagePrivate)) struct _ObexMessagePrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(ObexMessage, obex_message, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _obex_message_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _obex_message_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _obex_message_create_gdbus_proxy(ObexMessage *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void obex_message_dispose(GObject *gobject) { ObexMessage *self = OBEX_MESSAGE(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(obex_message_parent_class)->dispose(gobject); } static void obex_message_finalize (GObject *gobject) { ObexMessage *self = OBEX_MESSAGE(gobject); G_OBJECT_CLASS(obex_message_parent_class)->finalize(gobject); } static void obex_message_class_init(ObexMessageClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = obex_message_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _obex_message_get_property; gobject_class->set_property = _obex_message_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "ObexMessage D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void obex_message_init(ObexMessage *self) { self->priv = obex_message_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(session_conn != NULL); } static void _obex_message_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ObexMessage *self = OBEX_MESSAGE(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, obex_message_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _obex_message_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ObexMessage *self = OBEX_MESSAGE(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _obex_message_create_gdbus_proxy(self, OBEX_MESSAGE_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ObexMessage *obex_message_new(const gchar *dbus_object_path) { return g_object_new(OBEX_MESSAGE_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _obex_message_create_gdbus_proxy(ObexMessage *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(session_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, OBEX_MESSAGE_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "session", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *obex_message_get_dbus_object_path(ObexMessage *self) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* Properties access methods */ GVariant *obex_message_get_properties(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, error); } void obex_message_set_property(ObexMessage *self, const gchar *name, const GVariant *value, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, name, value, error); } void obex_message_set_deleted(ObexMessage *self, const gboolean value, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Deleted", g_variant_new_boolean(value), error); } const gchar *obex_message_get_folder(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Folder", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } gboolean obex_message_get_priority(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Priority", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } gboolean obex_message_get_protected(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Protected", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } gboolean obex_message_get_read(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Read", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } void obex_message_set_read(ObexMessage *self, const gboolean value, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Read", g_variant_new_boolean(value), error); } const gchar *obex_message_get_recipient(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Recipient", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *obex_message_get_recipient_address(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "RecipientAddress", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *obex_message_get_reply_to(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "ReplyTo", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *obex_message_get_sender(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Sender", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *obex_message_get_sender_address(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "SenderAddress", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } gboolean obex_message_get_sent(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Sent", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } guint64 obex_message_get_size(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Size", error); if(prop == NULL) return 0; guint64 ret = g_variant_get_uint64(prop); g_variant_unref(prop); return ret; } const gchar *obex_message_get_status(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Status", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *obex_message_get_subject(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Subject", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *obex_message_get_timestamp(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Timestamp", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *obex_message_get_message_type(ObexMessage *self, GError **error) { g_assert(OBEX_MESSAGE_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_MESSAGE_DBUS_INTERFACE, "Type", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_message.h000066400000000000000000000074161315563672100243450ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __OBEX_MESSAGE_H #define __OBEX_MESSAGE_H #ifdef __cplusplus extern "C" { #endif #include #define OBEX_MESSAGE_DBUS_SERVICE "org.bluez.obex" #define OBEX_MESSAGE_DBUS_INTERFACE "org.bluez.obex.Message1" /* * Type macros */ #define OBEX_MESSAGE_TYPE (obex_message_get_type()) #define OBEX_MESSAGE(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), OBEX_MESSAGE_TYPE, ObexMessage)) #define OBEX_MESSAGE_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), OBEX_MESSAGE_TYPE)) #define OBEX_MESSAGE_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), OBEX_MESSAGE_TYPE, ObexMessageClass)) #define OBEX_MESSAGE_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), OBEX_MESSAGE_TYPE)) #define OBEX_MESSAGE_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), OBEX_MESSAGE_TYPE, ObexMessageClass)) typedef struct _ObexMessage ObexMessage; typedef struct _ObexMessageClass ObexMessageClass; typedef struct _ObexMessagePrivate ObexMessagePrivate; struct _ObexMessage { GObject parent_instance; /*< private >*/ ObexMessagePrivate *priv; }; struct _ObexMessageClass { GObjectClass parent_class; }; /* used by OBEX_MESSAGE_TYPE */ GType obex_message_get_type(void) G_GNUC_CONST; /* * Constructor */ ObexMessage *obex_message_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *obex_message_get_dbus_object_path(ObexMessage *self); GVariant *obex_message_get_properties(ObexMessage *self, GError **error); void obex_message_set_property(ObexMessage *self, const gchar *name, const GVariant *value, GError **error); void obex_message_set_deleted(ObexMessage *self, const gboolean value, GError **error); const gchar *obex_message_get_folder(ObexMessage *self, GError **error); gboolean obex_message_get_priority(ObexMessage *self, GError **error); gboolean obex_message_get_protected(ObexMessage *self, GError **error); gboolean obex_message_get_read(ObexMessage *self, GError **error); void obex_message_set_read(ObexMessage *self, const gboolean value, GError **error); const gchar *obex_message_get_recipient(ObexMessage *self, GError **error); const gchar *obex_message_get_recipient_address(ObexMessage *self, GError **error); const gchar *obex_message_get_reply_to(ObexMessage *self, GError **error); const gchar *obex_message_get_sender(ObexMessage *self, GError **error); const gchar *obex_message_get_sender_address(ObexMessage *self, GError **error); gboolean obex_message_get_sent(ObexMessage *self, GError **error); guint64 obex_message_get_size(ObexMessage *self, GError **error); const gchar *obex_message_get_status(ObexMessage *self, GError **error); const gchar *obex_message_get_subject(ObexMessage *self, GError **error); const gchar *obex_message_get_timestamp(ObexMessage *self, GError **error); // This has been renamed because 'obex_message_get_type' is already used by GLib const gchar *obex_message_get_message_type(ObexMessage *self, GError **error); #ifdef __cplusplus } #endif #endif /* __OBEX_MESSAGE_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_message_access.c000066400000000000000000000153401315563672100256540ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../../dbus-common.h" #include "../../properties.h" #include "obex_message_access.h" #define OBEX_MESSAGE_ACCESS_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), OBEX_MESSAGE_ACCESS_TYPE, ObexMessageAccessPrivate)) struct _ObexMessageAccessPrivate { GDBusProxy *proxy; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(ObexMessageAccess, obex_message_access, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _obex_message_access_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _obex_message_access_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _obex_message_access_create_gdbus_proxy(ObexMessageAccess *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void obex_message_access_dispose(GObject *gobject) { ObexMessageAccess *self = OBEX_MESSAGE_ACCESS(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(obex_message_access_parent_class)->dispose(gobject); } static void obex_message_access_finalize (GObject *gobject) { ObexMessageAccess *self = OBEX_MESSAGE_ACCESS(gobject); G_OBJECT_CLASS(obex_message_access_parent_class)->finalize(gobject); } static void obex_message_access_class_init(ObexMessageAccessClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = obex_message_access_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _obex_message_access_get_property; gobject_class->set_property = _obex_message_access_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "ObexMessageAccess D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void obex_message_access_init(ObexMessageAccess *self) { self->priv = obex_message_access_get_instance_private (self); self->priv->proxy = NULL; self->priv->object_path = NULL; g_assert(session_conn != NULL); } static void _obex_message_access_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ObexMessageAccess *self = OBEX_MESSAGE_ACCESS(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, obex_message_access_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _obex_message_access_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ObexMessageAccess *self = OBEX_MESSAGE_ACCESS(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _obex_message_access_create_gdbus_proxy(self, OBEX_MESSAGE_ACCESS_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ObexMessageAccess *obex_message_access_new(const gchar *dbus_object_path) { return g_object_new(OBEX_MESSAGE_ACCESS_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _obex_message_access_create_gdbus_proxy(ObexMessageAccess *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(OBEX_MESSAGE_ACCESS_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(session_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, OBEX_MESSAGE_ACCESS_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* Get DBus object path */ const gchar *obex_message_access_get_dbus_object_path(ObexMessageAccess *self) { g_assert(OBEX_MESSAGE_ACCESS_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* array{string} ListFilterFields() */ const gchar **obex_message_access_list_filter_fields(ObexMessageAccess *self, GError **error) { g_assert(OBEX_MESSAGE_ACCESS_IS(self)); const gchar **ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "ListFilterFields", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return NULL; proxy_ret = g_variant_get_child_value(proxy_ret, 0); ret = g_variant_get_strv(proxy_ret, NULL); g_variant_unref(proxy_ret); return ret; } /* array{dict} ListFolders(dict filter) */ GVariant *obex_message_access_list_folders(ObexMessageAccess *self, const GVariant *filter, GError **error) { g_assert(OBEX_MESSAGE_ACCESS_IS(self)); GVariant *ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "ListFolders", g_variant_new ("(@a{sv})", filter), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return NULL; proxy_ret = g_variant_get_child_value(proxy_ret, 0); ret = g_variant_ref_sink(proxy_ret); g_variant_unref(proxy_ret); return ret; } /* void SetFolder(string name) */ void obex_message_access_set_folder(ObexMessageAccess *self, const gchar *name, GError **error) { g_assert(OBEX_MESSAGE_ACCESS_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "SetFolder", g_variant_new ("(s)", name), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void UpdateInbox(void) */ void obex_message_access_update_inbox(ObexMessageAccess *self, GError **error) { g_assert(OBEX_MESSAGE_ACCESS_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "UpdateInbox", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_message_access.h000066400000000000000000000055571315563672100256720ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __OBEX_MESSAGE_ACCESS_H #define __OBEX_MESSAGE_ACCESS_H #ifdef __cplusplus extern "C" { #endif #include #define OBEX_MESSAGE_ACCESS_DBUS_SERVICE "org.bluez.obex" #define OBEX_MESSAGE_ACCESS_DBUS_INTERFACE "org.bluez.obex.MessageAccess1" /* * Type macros */ #define OBEX_MESSAGE_ACCESS_TYPE (obex_message_access_get_type()) #define OBEX_MESSAGE_ACCESS(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), OBEX_MESSAGE_ACCESS_TYPE, ObexMessageAccess)) #define OBEX_MESSAGE_ACCESS_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), OBEX_MESSAGE_ACCESS_TYPE)) #define OBEX_MESSAGE_ACCESS_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), OBEX_MESSAGE_ACCESS_TYPE, ObexMessageAccessClass)) #define OBEX_MESSAGE_ACCESS_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), OBEX_MESSAGE_ACCESS_TYPE)) #define OBEX_MESSAGE_ACCESS_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), OBEX_MESSAGE_ACCESS_TYPE, ObexMessageAccessClass)) typedef struct _ObexMessageAccess ObexMessageAccess; typedef struct _ObexMessageAccessClass ObexMessageAccessClass; typedef struct _ObexMessageAccessPrivate ObexMessageAccessPrivate; struct _ObexMessageAccess { GObject parent_instance; /*< private >*/ ObexMessageAccessPrivate *priv; }; struct _ObexMessageAccessClass { GObjectClass parent_class; }; /* used by OBEX_MESSAGE_ACCESS_TYPE */ GType obex_message_access_get_type(void) G_GNUC_CONST; /* * Constructor */ ObexMessageAccess *obex_message_access_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *obex_message_access_get_dbus_object_path(ObexMessageAccess *self); const gchar **obex_message_access_list_filter_fields(ObexMessageAccess *self, GError **error); GVariant *obex_message_access_list_folders(ObexMessageAccess *self, const GVariant *filter, GError **error); void obex_message_access_set_folder(ObexMessageAccess *self, const gchar *name, GError **error); void obex_message_access_update_inbox(ObexMessageAccess *self, GError **error); #ifdef __cplusplus } #endif #endif /* __OBEX_MESSAGE_ACCESS_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_object_push.c000066400000000000000000000145501315563672100252160ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../../dbus-common.h" #include "../../properties.h" #include "obex_object_push.h" #define OBEX_OBJECT_PUSH_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), OBEX_OBJECT_PUSH_TYPE, ObexObjectPushPrivate)) struct _ObexObjectPushPrivate { GDBusProxy *proxy; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(ObexObjectPush, obex_object_push, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _obex_object_push_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _obex_object_push_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _obex_object_push_create_gdbus_proxy(ObexObjectPush *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void obex_object_push_dispose(GObject *gobject) { ObexObjectPush *self = OBEX_OBJECT_PUSH(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(obex_object_push_parent_class)->dispose(gobject); } static void obex_object_push_finalize (GObject *gobject) { ObexObjectPush *self = OBEX_OBJECT_PUSH(gobject); G_OBJECT_CLASS(obex_object_push_parent_class)->finalize(gobject); } static void obex_object_push_class_init(ObexObjectPushClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = obex_object_push_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _obex_object_push_get_property; gobject_class->set_property = _obex_object_push_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "ObexObjectPush D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void obex_object_push_init(ObexObjectPush *self) { self->priv = obex_object_push_get_instance_private (self); self->priv->proxy = NULL; self->priv->object_path = NULL; g_assert(session_conn != NULL); } static void _obex_object_push_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ObexObjectPush *self = OBEX_OBJECT_PUSH(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, obex_object_push_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _obex_object_push_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ObexObjectPush *self = OBEX_OBJECT_PUSH(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _obex_object_push_create_gdbus_proxy(self, OBEX_OBJECT_PUSH_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ObexObjectPush *obex_object_push_new(const gchar *dbus_object_path) { return g_object_new(OBEX_OBJECT_PUSH_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _obex_object_push_create_gdbus_proxy(ObexObjectPush *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(OBEX_OBJECT_PUSH_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(session_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, OBEX_OBJECT_PUSH_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* Get DBus object path */ const gchar *obex_object_push_get_dbus_object_path(ObexObjectPush *self) { g_assert(OBEX_OBJECT_PUSH_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } GVariant *obex_object_push_exchange_business_cards(ObexObjectPush *self, const gchar *clientfile, const gchar *targetfile, GError **error) { g_assert(OBEX_OBJECT_PUSH_IS(self)); GVariant *ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "ExchangeBusinessCards", g_variant_new ("(ss)", clientfile, targetfile), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return NULL; ret = g_variant_ref_sink(proxy_ret); g_variant_unref(proxy_ret); return ret; } GVariant *obex_object_push_pull_business_card(ObexObjectPush *self, const gchar *targetfile, GError **error) { g_assert(OBEX_OBJECT_PUSH_IS(self)); GVariant *ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "PullBusinessCard", g_variant_new ("(s)", targetfile), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return NULL; ret = g_variant_ref_sink(proxy_ret); g_variant_unref(proxy_ret); return ret; } GVariant *obex_object_push_send_file(ObexObjectPush *self, const gchar *sourcefile, GError **error) { g_assert(OBEX_OBJECT_PUSH_IS(self)); GVariant *ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "SendFile", g_variant_new ("(s)", sourcefile), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return NULL; ret = g_variant_ref_sink(proxy_ret); g_variant_unref(proxy_ret); return ret; }bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_object_push.h000066400000000000000000000053071315563672100252230ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __OBEX_OBJECT_PUSH_H #define __OBEX_OBJECT_PUSH_H #ifdef __cplusplus extern "C" { #endif #include #define OBEX_OBJECT_PUSH_DBUS_SERVICE "org.bluez.obex" #define OBEX_OBJECT_PUSH_DBUS_INTERFACE "org.bluez.obex.ObjectPush1" /* * Type macros */ #define OBEX_OBJECT_PUSH_TYPE (obex_object_push_get_type()) #define OBEX_OBJECT_PUSH(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), OBEX_OBJECT_PUSH_TYPE, ObexObjectPush)) #define OBEX_OBJECT_PUSH_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), OBEX_OBJECT_PUSH_TYPE)) #define OBEX_OBJECT_PUSH_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), OBEX_OBJECT_PUSH_TYPE, ObexObjectPushClass)) #define OBEX_OBJECT_PUSH_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), OBEX_OBJECT_PUSH_TYPE)) #define OBEX_OBJECT_PUSH_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), OBEX_OBJECT_PUSH_TYPE, ObexObjectPushClass)) typedef struct _ObexObjectPush ObexObjectPush; typedef struct _ObexObjectPushClass ObexObjectPushClass; typedef struct _ObexObjectPushPrivate ObexObjectPushPrivate; struct _ObexObjectPush { GObject parent_instance; /*< private >*/ ObexObjectPushPrivate *priv; }; struct _ObexObjectPushClass { GObjectClass parent_class; }; /* used by OBEX_OBJECT_PUSH_TYPE */ GType obex_object_push_get_type(void) G_GNUC_CONST; /* * Constructor */ ObexObjectPush *obex_object_push_new(const gchar *dbus_object_path); const gchar *obex_object_push_get_dbus_object_path(ObexObjectPush *self); GVariant *obex_object_push_exchange_business_cards(ObexObjectPush *self, const gchar *clientfile, const gchar *targetfile, GError **error); GVariant *obex_object_push_pull_business_card(ObexObjectPush *self, const gchar *targetfile, GError **error); GVariant *obex_object_push_send_file(ObexObjectPush *self, const gchar *sourcefile, GError **error); #ifdef __cplusplus } #endif #endif /* __OBEX_OBJECT_PUSH_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_phonebook_access.c000066400000000000000000000150521315563672100262140ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../../dbus-common.h" #include "../../properties.h" #include "obex_phonebook_access.h" #define OBEX_PHONEBOOK_ACCESS_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), OBEX_PHONEBOOK_ACCESS_TYPE, ObexPhonebookAccessPrivate)) struct _ObexPhonebookAccessPrivate { GDBusProxy *proxy; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(ObexPhonebookAccess, obex_phonebook_access, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _obex_phonebook_access_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _obex_phonebook_access_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _obex_phonebook_access_create_gdbus_proxy(ObexPhonebookAccess *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void obex_phonebook_access_dispose(GObject *gobject) { ObexPhonebookAccess *self = OBEX_PHONEBOOK_ACCESS(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(obex_phonebook_access_parent_class)->dispose(gobject); } static void obex_phonebook_access_finalize (GObject *gobject) { ObexPhonebookAccess *self = OBEX_PHONEBOOK_ACCESS(gobject); G_OBJECT_CLASS(obex_phonebook_access_parent_class)->finalize(gobject); } static void obex_phonebook_access_class_init(ObexPhonebookAccessClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = obex_phonebook_access_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _obex_phonebook_access_get_property; gobject_class->set_property = _obex_phonebook_access_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "ObexPhonebookAccess D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void obex_phonebook_access_init(ObexPhonebookAccess *self) { self->priv = obex_phonebook_access_get_instance_private (self); self->priv->proxy = NULL; self->priv->object_path = NULL; g_assert(session_conn != NULL); } static void _obex_phonebook_access_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ObexPhonebookAccess *self = OBEX_PHONEBOOK_ACCESS(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, obex_phonebook_access_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _obex_phonebook_access_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ObexPhonebookAccess *self = OBEX_PHONEBOOK_ACCESS(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _obex_phonebook_access_create_gdbus_proxy(self, OBEX_PHONEBOOK_ACCESS_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ObexPhonebookAccess *obex_phonebook_access_new(const gchar *dbus_object_path) { return g_object_new(OBEX_PHONEBOOK_ACCESS_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _obex_phonebook_access_create_gdbus_proxy(ObexPhonebookAccess *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(OBEX_PHONEBOOK_ACCESS_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(session_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, OBEX_PHONEBOOK_ACCESS_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* Get DBus object path */ const gchar *obex_phonebook_access_get_dbus_object_path(ObexPhonebookAccess *self) { g_assert(OBEX_PHONEBOOK_ACCESS_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* uint16 GetSize() */ guint16 obex_phonebook_access_get_size(ObexPhonebookAccess *self, GError **error) { g_assert(OBEX_PHONEBOOK_ACCESS_IS(self)); guint16 ret = 0; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "GetSize", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return 0; proxy_ret = g_variant_get_child_value(proxy_ret, 0); ret = g_variant_get_uint16(proxy_ret); g_variant_unref(proxy_ret); return ret; } /* array{string} ListFilterFields() */ const gchar **obex_phonebook_access_list_filter_fields(ObexPhonebookAccess *self, GError **error) { g_assert(OBEX_PHONEBOOK_ACCESS_IS(self)); const gchar **ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "ListFilterFields", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return NULL; proxy_ret = g_variant_get_child_value(proxy_ret, 0); ret = g_variant_get_strv(proxy_ret, NULL); g_variant_unref(proxy_ret); return ret; } /* void Select(string location, string phonebook) */ void obex_phonebook_access_select(ObexPhonebookAccess *self, const gchar *location, const gchar *phonebook, GError **error) { g_assert(OBEX_PHONEBOOK_ACCESS_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Select", g_variant_new ("(ss)", location, phonebook), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_phonebook_access.h000066400000000000000000000055551315563672100262300ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __OBEX_PHONEBOOK_ACCESS_H #define __OBEX_PHONEBOOK_ACCESS_H #ifdef __cplusplus extern "C" { #endif #include #define OBEX_PHONEBOOK_ACCESS_DBUS_SERVICE "org.bluez.obex" #define OBEX_PHONEBOOK_ACCESS_DBUS_INTERFACE "org.bluez.obex.PhonebookAccess1" /* * Type macros */ #define OBEX_PHONEBOOK_ACCESS_TYPE (obex_phonebook_access_get_type()) #define OBEX_PHONEBOOK_ACCESS(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), OBEX_PHONEBOOK_ACCESS_TYPE, ObexPhonebookAccess)) #define OBEX_PHONEBOOK_ACCESS_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), OBEX_PHONEBOOK_ACCESS_TYPE)) #define OBEX_PHONEBOOK_ACCESS_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), OBEX_PHONEBOOK_ACCESS_TYPE, ObexPhonebookAccessClass)) #define OBEX_PHONEBOOK_ACCESS_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), OBEX_PHONEBOOK_ACCESS_TYPE)) #define OBEX_PHONEBOOK_ACCESS_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), OBEX_PHONEBOOK_ACCESS_TYPE, ObexPhonebookAccessClass)) typedef struct _ObexPhonebookAccess ObexPhonebookAccess; typedef struct _ObexPhonebookAccessClass ObexPhonebookAccessClass; typedef struct _ObexPhonebookAccessPrivate ObexPhonebookAccessPrivate; struct _ObexPhonebookAccess { GObject parent_instance; /*< private >*/ ObexPhonebookAccessPrivate *priv; }; struct _ObexPhonebookAccessClass { GObjectClass parent_class; }; /* used by OBEX_PHONEBOOK_ACCESS_TYPE */ GType obex_phonebook_access_get_type(void) G_GNUC_CONST; /* * Constructor */ ObexPhonebookAccess *obex_phonebook_access_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *obex_phonebook_access_get_dbus_object_path(ObexPhonebookAccess *self); guint16 obex_phonebook_access_get_size(ObexPhonebookAccess *self, GError **error); const gchar **obex_phonebook_access_list_filter_fields(ObexPhonebookAccess *self, GError **error); void obex_phonebook_access_select(ObexPhonebookAccess *self, const gchar *location, const gchar *phonebook, GError **error); #ifdef __cplusplus } #endif #endif /* __OBEX_PHONEBOOK_ACCESS_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_session.c000066400000000000000000000200041315563672100243630ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../../dbus-common.h" #include "../../properties.h" #include "obex_session.h" #define OBEX_SESSION_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), OBEX_SESSION_TYPE, ObexSessionPrivate)) struct _ObexSessionPrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(ObexSession, obex_session, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _obex_session_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _obex_session_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _obex_session_create_gdbus_proxy(ObexSession *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void obex_session_dispose(GObject *gobject) { ObexSession *self = OBEX_SESSION(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(obex_session_parent_class)->dispose(gobject); } static void obex_session_finalize (GObject *gobject) { ObexSession *self = OBEX_SESSION(gobject); G_OBJECT_CLASS(obex_session_parent_class)->finalize(gobject); } static void obex_session_class_init(ObexSessionClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = obex_session_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _obex_session_get_property; gobject_class->set_property = _obex_session_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "ObexSession D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void obex_session_init(ObexSession *self) { self->priv = obex_session_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(session_conn != NULL); } static void _obex_session_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ObexSession *self = OBEX_SESSION(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, obex_session_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _obex_session_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ObexSession *self = OBEX_SESSION(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _obex_session_create_gdbus_proxy(self, OBEX_SESSION_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ObexSession *obex_session_new(const gchar *dbus_object_path) { return g_object_new(OBEX_SESSION_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _obex_session_create_gdbus_proxy(ObexSession *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(OBEX_SESSION_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(session_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, OBEX_SESSION_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "session", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *obex_session_get_dbus_object_path(ObexSession *self) { g_assert(OBEX_SESSION_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* string GetCapabilities() */ const gchar *obex_session_get_capabilities(ObexSession *self, GError **error) { g_assert(OBEX_SESSION_IS(self)); const gchar *ret = NULL; GVariant *proxy_ret = g_dbus_proxy_call_sync(self->priv->proxy, "GetCapabilities", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (proxy_ret != NULL) return NULL; proxy_ret = g_variant_get_child_value(proxy_ret, 0); ret = g_variant_get_string(proxy_ret, NULL); g_variant_unref(proxy_ret); return ret; } /* Properties access methods */ GVariant *obex_session_get_properties(ObexSession *self, GError **error) { g_assert(OBEX_SESSION_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, OBEX_SESSION_DBUS_INTERFACE, error); } void obex_session_set_property(ObexSession *self, const gchar *name, const GVariant *value, GError **error) { g_assert(OBEX_SESSION_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, OBEX_SESSION_DBUS_INTERFACE, name, value, error); } guint8 obex_session_get_channel(ObexSession *self, GError **error) { g_assert(OBEX_SESSION_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_SESSION_DBUS_INTERFACE, "Channel", error); if(prop == NULL) return 0; guchar ret = g_variant_get_byte(prop); g_variant_unref(prop); return ret; } const gchar *obex_session_get_destination(ObexSession *self, GError **error) { g_assert(OBEX_SESSION_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_SESSION_DBUS_INTERFACE, "Destination", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *obex_session_get_root(ObexSession *self, GError **error) { g_assert(OBEX_SESSION_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_SESSION_DBUS_INTERFACE, "Root", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *obex_session_get_source(ObexSession *self, GError **error) { g_assert(OBEX_SESSION_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_SESSION_DBUS_INTERFACE, "Source", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *obex_session_get_target(ObexSession *self, GError **error) { g_assert(OBEX_SESSION_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_SESSION_DBUS_INTERFACE, "Target", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_session.h000066400000000000000000000055701315563672100244030ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __OBEX_SESSION_H #define __OBEX_SESSION_H #ifdef __cplusplus extern "C" { #endif #include #define OBEX_SESSION_DBUS_SERVICE "org.bluez.obex" #define OBEX_SESSION_DBUS_INTERFACE "org.bluez.obex.Session1" /* * Type macros */ #define OBEX_SESSION_TYPE (obex_session_get_type()) #define OBEX_SESSION(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), OBEX_SESSION_TYPE, ObexSession)) #define OBEX_SESSION_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), OBEX_SESSION_TYPE)) #define OBEX_SESSION_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), OBEX_SESSION_TYPE, ObexSessionClass)) #define OBEX_SESSION_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), OBEX_SESSION_TYPE)) #define OBEX_SESSION_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), OBEX_SESSION_TYPE, ObexSessionClass)) typedef struct _ObexSession ObexSession; typedef struct _ObexSessionClass ObexSessionClass; typedef struct _ObexSessionPrivate ObexSessionPrivate; struct _ObexSession { GObject parent_instance; /*< private >*/ ObexSessionPrivate *priv; }; struct _ObexSessionClass { GObjectClass parent_class; }; /* used by OBEX_SESSION_TYPE */ GType obex_session_get_type(void) G_GNUC_CONST; /* * Constructor */ ObexSession *obex_session_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *obex_session_get_dbus_object_path(ObexSession *self); const gchar *obex_session_get_capabilities(ObexSession *self, GError **error); GVariant *obex_session_get_properties(ObexSession *self, GError **error); void obex_session_set_property(ObexSession *self, const gchar *name, const GVariant *value, GError **error); guint8 obex_session_get_channel(ObexSession *self, GError **error); const gchar *obex_session_get_destination(ObexSession *self, GError **error); const gchar *obex_session_get_root(ObexSession *self, GError **error); const gchar *obex_session_get_source(ObexSession *self, GError **error); const gchar *obex_session_get_target(ObexSession *self, GError **error); #ifdef __cplusplus } #endif #endif /* __OBEX_SESSION_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_synchronization.c000066400000000000000000000130021315563672100261410ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../../dbus-common.h" #include "../../properties.h" #include "obex_synchronization.h" #define OBEX_SYNCHRONIZATION_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), OBEX_SYNCHRONIZATION_TYPE, ObexSynchronizationPrivate)) struct _ObexSynchronizationPrivate { GDBusProxy *proxy; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(ObexSynchronization, obex_synchronization, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _obex_synchronization_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _obex_synchronization_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _obex_synchronization_create_gdbus_proxy(ObexSynchronization *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void obex_synchronization_dispose(GObject *gobject) { ObexSynchronization *self = OBEX_SYNCHRONIZATION(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(obex_synchronization_parent_class)->dispose(gobject); } static void obex_synchronization_finalize (GObject *gobject) { ObexSynchronization *self = OBEX_SYNCHRONIZATION(gobject); G_OBJECT_CLASS(obex_synchronization_parent_class)->finalize(gobject); } static void obex_synchronization_class_init(ObexSynchronizationClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = obex_synchronization_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _obex_synchronization_get_property; gobject_class->set_property = _obex_synchronization_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "ObexSynchronization D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void obex_synchronization_init(ObexSynchronization *self) { self->priv = obex_synchronization_get_instance_private (self); self->priv->proxy = NULL; self->priv->object_path = NULL; g_assert(session_conn != NULL); } static void _obex_synchronization_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ObexSynchronization *self = OBEX_SYNCHRONIZATION(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, obex_synchronization_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _obex_synchronization_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ObexSynchronization *self = OBEX_SYNCHRONIZATION(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _obex_synchronization_create_gdbus_proxy(self, OBEX_SYNCHRONIZATION_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ObexSynchronization *obex_synchronization_new(const gchar *dbus_object_path) { return g_object_new(OBEX_SYNCHRONIZATION_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _obex_synchronization_create_gdbus_proxy(ObexSynchronization *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(OBEX_SYNCHRONIZATION_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(session_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, OBEX_SYNCHRONIZATION_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* Get DBus object path */ const gchar *obex_synchronization_get_dbus_object_path(ObexSynchronization *self) { g_assert(OBEX_SYNCHRONIZATION_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* void SetLocation(string location) */ void obex_synchronization_set_location(ObexSynchronization *self, const gchar *location, GError **error) { g_assert(OBEX_SYNCHRONIZATION_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "SetLocation", g_variant_new ("(s)", location), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_synchronization.h000066400000000000000000000052171315563672100261570ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __OBEX_SYNCHRONIZATION_H #define __OBEX_SYNCHRONIZATION_H #ifdef __cplusplus extern "C" { #endif #include #define OBEX_SYNCHRONIZATION_DBUS_SERVICE "org.bluez.obex" #define OBEX_SYNCHRONIZATION_DBUS_INTERFACE "org.bluez.obex.Synchronization1" /* * Type macros */ #define OBEX_SYNCHRONIZATION_TYPE (obex_synchronization_get_type()) #define OBEX_SYNCHRONIZATION(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), OBEX_SYNCHRONIZATION_TYPE, ObexSynchronization)) #define OBEX_SYNCHRONIZATION_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), OBEX_SYNCHRONIZATION_TYPE)) #define OBEX_SYNCHRONIZATION_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), OBEX_SYNCHRONIZATION_TYPE, ObexSynchronizationClass)) #define OBEX_SYNCHRONIZATION_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), OBEX_SYNCHRONIZATION_TYPE)) #define OBEX_SYNCHRONIZATION_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), OBEX_SYNCHRONIZATION_TYPE, ObexSynchronizationClass)) typedef struct _ObexSynchronization ObexSynchronization; typedef struct _ObexSynchronizationClass ObexSynchronizationClass; typedef struct _ObexSynchronizationPrivate ObexSynchronizationPrivate; struct _ObexSynchronization { GObject parent_instance; /*< private >*/ ObexSynchronizationPrivate *priv; }; struct _ObexSynchronizationClass { GObjectClass parent_class; }; /* used by OBEX_SYNCHRONIZATION_TYPE */ GType obex_synchronization_get_type(void) G_GNUC_CONST; /* * Constructor */ ObexSynchronization *obex_synchronization_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *obex_synchronization_get_dbus_object_path(ObexSynchronization *self); void obex_synchronization_set_location(ObexSynchronization *self, const gchar *location, GError **error); #ifdef __cplusplus } #endif #endif /* __OBEX_SYNCHRONIZATION_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_transfer.c000066400000000000000000000225551315563672100245410ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../../dbus-common.h" #include "../../properties.h" #include "obex_transfer.h" #define OBEX_TRANSFER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), OBEX_TRANSFER_TYPE, ObexTransferPrivate)) struct _ObexTransferPrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(ObexTransfer, obex_transfer, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _obex_transfer_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _obex_transfer_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _obex_transfer_create_gdbus_proxy(ObexTransfer *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void obex_transfer_dispose(GObject *gobject) { ObexTransfer *self = OBEX_TRANSFER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(obex_transfer_parent_class)->dispose(gobject); } static void obex_transfer_finalize (GObject *gobject) { ObexTransfer *self = OBEX_TRANSFER(gobject); G_OBJECT_CLASS(obex_transfer_parent_class)->finalize(gobject); } static void obex_transfer_class_init(ObexTransferClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = obex_transfer_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _obex_transfer_get_property; gobject_class->set_property = _obex_transfer_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "ObexTransfer D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void obex_transfer_init(ObexTransfer *self) { self->priv = obex_transfer_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(session_conn != NULL); } static void _obex_transfer_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ObexTransfer *self = OBEX_TRANSFER(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, obex_transfer_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _obex_transfer_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ObexTransfer *self = OBEX_TRANSFER(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _obex_transfer_create_gdbus_proxy(self, OBEX_TRANSFER_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ObexTransfer *obex_transfer_new(const gchar *dbus_object_path) { return g_object_new(OBEX_TRANSFER_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _obex_transfer_create_gdbus_proxy(ObexTransfer *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(session_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, OBEX_TRANSFER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "session", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *obex_transfer_get_dbus_object_path(ObexTransfer *self) { g_assert(OBEX_TRANSFER_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* void Cancel() */ void obex_transfer_cancel(ObexTransfer *self, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Cancel", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Resume() */ void obex_transfer_resume(ObexTransfer *self, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Resume", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void Suspend() */ void obex_transfer_suspend(ObexTransfer *self, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Suspend", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* Properties access methods */ GVariant *obex_transfer_get_properties(ObexTransfer *self, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, OBEX_TRANSFER_DBUS_INTERFACE, error); } void obex_transfer_set_property(ObexTransfer *self, const gchar *name, const GVariant *value, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, OBEX_TRANSFER_DBUS_INTERFACE, name, value, error); } const gchar *obex_transfer_get_filename(ObexTransfer *self, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_TRANSFER_DBUS_INTERFACE, "Filename", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *obex_transfer_get_name(ObexTransfer *self, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_TRANSFER_DBUS_INTERFACE, "Name", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *obex_transfer_get_session(ObexTransfer *self, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_TRANSFER_DBUS_INTERFACE, "Session", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } guint64 obex_transfer_get_size(ObexTransfer *self, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_TRANSFER_DBUS_INTERFACE, "Size", error); if(prop == NULL) return 0; guint64 ret = g_variant_get_uint64(prop); g_variant_unref(prop); return ret; } const gchar *obex_transfer_get_status(ObexTransfer *self, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_TRANSFER_DBUS_INTERFACE, "Status", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } guint64 obex_transfer_get_time(ObexTransfer *self, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_TRANSFER_DBUS_INTERFACE, "Time", error); if(prop == NULL) return 0; guint64 ret = g_variant_get_uint64(prop); g_variant_unref(prop); return ret; } guint64 obex_transfer_get_transferred(ObexTransfer *self, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_TRANSFER_DBUS_INTERFACE, "Transferred", error); if(prop == NULL) return 0; guint64 ret = g_variant_get_uint64(prop); g_variant_unref(prop); return ret; } const gchar *obex_transfer_get_transfer_type(ObexTransfer *self, GError **error) { g_assert(OBEX_TRANSFER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, OBEX_TRANSFER_DBUS_INTERFACE, "Type", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/obex/obex_transfer.h000066400000000000000000000065101315563672100245370ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __OBEX_TRANSFER_H #define __OBEX_TRANSFER_H #ifdef __cplusplus extern "C" { #endif #include #define OBEX_TRANSFER_DBUS_SERVICE "org.bluez.obex" #define OBEX_TRANSFER_DBUS_INTERFACE "org.bluez.obex.Transfer1" /* * Type macros */ #define OBEX_TRANSFER_TYPE (obex_transfer_get_type()) #define OBEX_TRANSFER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), OBEX_TRANSFER_TYPE, ObexTransfer)) #define OBEX_TRANSFER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), OBEX_TRANSFER_TYPE)) #define OBEX_TRANSFER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), OBEX_TRANSFER_TYPE, ObexTransferClass)) #define OBEX_TRANSFER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), OBEX_TRANSFER_TYPE)) #define OBEX_TRANSFER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), OBEX_TRANSFER_TYPE, ObexTransferClass)) typedef struct _ObexTransfer ObexTransfer; typedef struct _ObexTransferClass ObexTransferClass; typedef struct _ObexTransferPrivate ObexTransferPrivate; struct _ObexTransfer { GObject parent_instance; /*< private >*/ ObexTransferPrivate *priv; }; struct _ObexTransferClass { GObjectClass parent_class; }; /* used by OBEX_TRANSFER_TYPE */ GType obex_transfer_get_type(void) G_GNUC_CONST; /* * Constructor */ ObexTransfer *obex_transfer_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *obex_transfer_get_dbus_object_path(ObexTransfer *self); void obex_transfer_cancel(ObexTransfer *self, GError **error); void obex_transfer_resume(ObexTransfer *self, GError **error); void obex_transfer_suspend(ObexTransfer *self, GError **error); GVariant *obex_transfer_get_properties(ObexTransfer *self, GError **error); void obex_transfer_set_property(ObexTransfer *self, const gchar *name, const GVariant *value, GError **error); const gchar *obex_transfer_get_filename(ObexTransfer *self, GError **error); const gchar *obex_transfer_get_name(ObexTransfer *self, GError **error); const gchar *obex_transfer_get_session(ObexTransfer *self, GError **error); guint64 obex_transfer_get_size(ObexTransfer *self, GError **error); const gchar *obex_transfer_get_status(ObexTransfer *self, GError **error); guint64 obex_transfer_get_time(ObexTransfer *self, GError **error); guint64 obex_transfer_get_transferred(ObexTransfer *self, GError **error); // This has been renamed because 'obex_transfer_get_type' is already used by GLib const gchar *obex_transfer_get_transfer_type(ObexTransfer *self, GError **error); #ifdef __cplusplus } #endif #endif /* __OBEX_TRANSFER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/profile_manager.c000066400000000000000000000114301315563672100240630ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "profile_manager.h" #define PROFILE_MANAGER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), PROFILE_MANAGER_TYPE, ProfileManagerPrivate)) struct _ProfileManagerPrivate { GDBusProxy *proxy; }; G_DEFINE_TYPE_WITH_PRIVATE(ProfileManager, profile_manager, G_TYPE_OBJECT); enum { PROP_0, }; static void _profile_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _profile_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _profile_manager_create_gdbus_proxy(ProfileManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void profile_manager_dispose(GObject *gobject) { ProfileManager *self = PROFILE_MANAGER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Chain up to the parent class */ G_OBJECT_CLASS(profile_manager_parent_class)->dispose(gobject); } static void profile_manager_finalize (GObject *gobject) { ProfileManager *self = PROFILE_MANAGER(gobject); G_OBJECT_CLASS(profile_manager_parent_class)->finalize(gobject); } static void profile_manager_class_init(ProfileManagerClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = profile_manager_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _profile_manager_get_property; gobject_class->set_property = _profile_manager_set_property; if (pspec) g_param_spec_unref(pspec); } static void profile_manager_init(ProfileManager *self) { self->priv = profile_manager_get_instance_private (self); self->priv->proxy = NULL; g_assert(system_conn != NULL); GError *error = NULL; _profile_manager_create_gdbus_proxy(self, PROFILE_MANAGER_DBUS_SERVICE, PROFILE_MANAGER_DBUS_PATH, &error); g_assert(error == NULL); } static void _profile_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ProfileManager *self = PROFILE_MANAGER(object); switch (property_id) { default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _profile_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ProfileManager *self = PROFILE_MANAGER(object); GError *error = NULL; switch (property_id) { default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ProfileManager *profile_manager_new() { return g_object_new(PROFILE_MANAGER_TYPE, NULL); } /* Private DBus proxy creation */ static void _profile_manager_create_gdbus_proxy(ProfileManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(PROFILE_MANAGER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, PROFILE_MANAGER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* void RegisterProfile(object profile, string uuid, dict options) */ void profile_manager_register_profile(ProfileManager *self, const gchar *profile, const gchar *uuid, const GVariant *options, GError **error) { g_assert(PROFILE_MANAGER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "RegisterProfile", g_variant_new ("(os@a{sv})", profile, uuid, options), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* void UnregisterProfile(object profile) */ void profile_manager_unregister_profile(ProfileManager *self, const gchar *profile, GError **error) { g_assert(PROFILE_MANAGER_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "UnregisterProfile", g_variant_new ("(o)", profile), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/profile_manager.h000066400000000000000000000050471315563672100240770ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __PROFILE_MANAGER_H #define __PROFILE_MANAGER_H #ifdef __cplusplus extern "C" { #endif #include #define PROFILE_MANAGER_DBUS_SERVICE "org.bluez" #define PROFILE_MANAGER_DBUS_INTERFACE "org.bluez.ProfileManager1" #define PROFILE_MANAGER_DBUS_PATH "/org/bluez" /* * Type macros */ #define PROFILE_MANAGER_TYPE (profile_manager_get_type()) #define PROFILE_MANAGER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), PROFILE_MANAGER_TYPE, ProfileManager)) #define PROFILE_MANAGER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), PROFILE_MANAGER_TYPE)) #define PROFILE_MANAGER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), PROFILE_MANAGER_TYPE, ProfileManagerClass)) #define PROFILE_MANAGER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), PROFILE_MANAGER_TYPE)) #define PROFILE_MANAGER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), PROFILE_MANAGER_TYPE, ProfileManagerClass)) typedef struct _ProfileManager ProfileManager; typedef struct _ProfileManagerClass ProfileManagerClass; typedef struct _ProfileManagerPrivate ProfileManagerPrivate; struct _ProfileManager { GObject parent_instance; /*< private >*/ ProfileManagerPrivate *priv; }; struct _ProfileManagerClass { GObjectClass parent_class; }; /* used by PROFILE_MANAGER_TYPE */ GType profile_manager_get_type(void) G_GNUC_CONST; /* * Constructor */ ProfileManager *profile_manager_new(); /* * Method definitions */ void profile_manager_register_profile(ProfileManager *self, const gchar *profile, const gchar *uuid, const GVariant *options, GError **error); void profile_manager_unregister_profile(ProfileManager *self, const gchar *profile, GError **error); #ifdef __cplusplus } #endif #endif /* __PROFILE_MANAGER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/proximity_monitor.c000066400000000000000000000175151315563672100245560ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "proximity_monitor.h" #define PROXIMITY_MONITOR_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), PROXIMITY_MONITOR_TYPE, ProximityMonitorPrivate)) struct _ProximityMonitorPrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(ProximityMonitor, proximity_monitor, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _proximity_monitor_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _proximity_monitor_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _proximity_monitor_create_gdbus_proxy(ProximityMonitor *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void proximity_monitor_dispose(GObject *gobject) { ProximityMonitor *self = PROXIMITY_MONITOR(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(proximity_monitor_parent_class)->dispose(gobject); } static void proximity_monitor_finalize (GObject *gobject) { ProximityMonitor *self = PROXIMITY_MONITOR(gobject); G_OBJECT_CLASS(proximity_monitor_parent_class)->finalize(gobject); } static void proximity_monitor_class_init(ProximityMonitorClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = proximity_monitor_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _proximity_monitor_get_property; gobject_class->set_property = _proximity_monitor_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "ProximityMonitor D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void proximity_monitor_init(ProximityMonitor *self) { self->priv = proximity_monitor_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _proximity_monitor_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ProximityMonitor *self = PROXIMITY_MONITOR(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, proximity_monitor_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _proximity_monitor_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ProximityMonitor *self = PROXIMITY_MONITOR(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _proximity_monitor_create_gdbus_proxy(self, PROXIMITY_MONITOR_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ProximityMonitor *proximity_monitor_new(const gchar *dbus_object_path) { return g_object_new(PROXIMITY_MONITOR_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _proximity_monitor_create_gdbus_proxy(ProximityMonitor *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(PROXIMITY_MONITOR_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, PROXIMITY_MONITOR_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "system", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *proximity_monitor_get_dbus_object_path(ProximityMonitor *self) { g_assert(PROXIMITY_MONITOR_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* Properties access methods */ GVariant *proximity_monitor_get_properties(ProximityMonitor *self, GError **error) { g_assert(PROXIMITY_MONITOR_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, PROXIMITY_MONITOR_DBUS_INTERFACE, error); } void proximity_monitor_set_property(ProximityMonitor *self, const gchar *name, const GVariant *value, GError **error) { g_assert(PROXIMITY_MONITOR_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, PROXIMITY_MONITOR_DBUS_INTERFACE, name, value, error); } const gchar *proximity_monitor_get_immediate_alert_level(ProximityMonitor *self, GError **error) { g_assert(PROXIMITY_MONITOR_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, PROXIMITY_MONITOR_DBUS_INTERFACE, "ImmediateAlertLevel", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } void proximity_monitor_set_immediate_alert_level(ProximityMonitor *self, const gchar *value, GError **error) { g_assert(PROXIMITY_MONITOR_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, PROXIMITY_MONITOR_DBUS_INTERFACE, "ImmediateAlertLevel", g_variant_new_string(value), error); } const gchar *proximity_monitor_get_link_loss_alert_level(ProximityMonitor *self, GError **error) { g_assert(PROXIMITY_MONITOR_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, PROXIMITY_MONITOR_DBUS_INTERFACE, "LinkLossAlertLevel", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } void proximity_monitor_set_link_loss_alert_level(ProximityMonitor *self, const gchar *value, GError **error) { g_assert(PROXIMITY_MONITOR_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, PROXIMITY_MONITOR_DBUS_INTERFACE, "LinkLossAlertLevel", g_variant_new_string(value), error); } const gchar *proximity_monitor_get_signal_level(ProximityMonitor *self, GError **error) { g_assert(PROXIMITY_MONITOR_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, PROXIMITY_MONITOR_DBUS_INTERFACE, "SignalLevel", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/proximity_monitor.h000066400000000000000000000061701315563672100245560ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __PROXIMITY_MONITOR_H #define __PROXIMITY_MONITOR_H #ifdef __cplusplus extern "C" { #endif #include #define PROXIMITY_MONITOR_DBUS_SERVICE "org.bluez" #define PROXIMITY_MONITOR_DBUS_INTERFACE "org.bluez.ProximityMonitor1" /* * Type macros */ #define PROXIMITY_MONITOR_TYPE (proximity_monitor_get_type()) #define PROXIMITY_MONITOR(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), PROXIMITY_MONITOR_TYPE, ProximityMonitor)) #define PROXIMITY_MONITOR_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), PROXIMITY_MONITOR_TYPE)) #define PROXIMITY_MONITOR_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), PROXIMITY_MONITOR_TYPE, ProximityMonitorClass)) #define PROXIMITY_MONITOR_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), PROXIMITY_MONITOR_TYPE)) #define PROXIMITY_MONITOR_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), PROXIMITY_MONITOR_TYPE, ProximityMonitorClass)) typedef struct _ProximityMonitor ProximityMonitor; typedef struct _ProximityMonitorClass ProximityMonitorClass; typedef struct _ProximityMonitorPrivate ProximityMonitorPrivate; struct _ProximityMonitor { GObject parent_instance; /*< private >*/ ProximityMonitorPrivate *priv; }; struct _ProximityMonitorClass { GObjectClass parent_class; }; /* used by PROXIMITY_MONITOR_TYPE */ GType proximity_monitor_get_type(void) G_GNUC_CONST; /* * Constructor */ ProximityMonitor *proximity_monitor_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *proximity_monitor_get_dbus_object_path(ProximityMonitor *self); GVariant *proximity_monitor_get_properties(ProximityMonitor *self, GError **error); void proximity_monitor_set_property(ProximityMonitor *self, const gchar *name, const GVariant *value, GError **error); const gchar *proximity_monitor_get_immediate_alert_level(ProximityMonitor *self, GError **error); void proximity_monitor_set_immediate_alert_level(ProximityMonitor *self, const gchar *value, GError **error); const gchar *proximity_monitor_get_link_loss_alert_level(ProximityMonitor *self, GError **error); void proximity_monitor_set_link_loss_alert_level(ProximityMonitor *self, const gchar *value, GError **error); const gchar *proximity_monitor_get_signal_level(ProximityMonitor *self, GError **error); #ifdef __cplusplus } #endif #endif /* __PROXIMITY_MONITOR_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/proximity_reporter.c000066400000000000000000000155341315563672100247300ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "proximity_reporter.h" #define PROXIMITY_REPORTER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), PROXIMITY_REPORTER_TYPE, ProximityReporterPrivate)) struct _ProximityReporterPrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(ProximityReporter, proximity_reporter, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _proximity_reporter_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _proximity_reporter_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _proximity_reporter_create_gdbus_proxy(ProximityReporter *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void proximity_reporter_dispose(GObject *gobject) { ProximityReporter *self = PROXIMITY_REPORTER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(proximity_reporter_parent_class)->dispose(gobject); } static void proximity_reporter_finalize (GObject *gobject) { ProximityReporter *self = PROXIMITY_REPORTER(gobject); G_OBJECT_CLASS(proximity_reporter_parent_class)->finalize(gobject); } static void proximity_reporter_class_init(ProximityReporterClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = proximity_reporter_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _proximity_reporter_get_property; gobject_class->set_property = _proximity_reporter_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "ProximityReporter D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void proximity_reporter_init(ProximityReporter *self) { self->priv = proximity_reporter_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _proximity_reporter_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ProximityReporter *self = PROXIMITY_REPORTER(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, proximity_reporter_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _proximity_reporter_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ProximityReporter *self = PROXIMITY_REPORTER(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _proximity_reporter_create_gdbus_proxy(self, PROXIMITY_REPORTER_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ProximityReporter *proximity_reporter_new(const gchar *dbus_object_path) { return g_object_new(PROXIMITY_REPORTER_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _proximity_reporter_create_gdbus_proxy(ProximityReporter *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(PROXIMITY_REPORTER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, PROXIMITY_REPORTER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "system", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *proximity_reporter_get_dbus_object_path(ProximityReporter *self) { g_assert(PROXIMITY_REPORTER_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* Properties access methods */ GVariant *proximity_reporter_get_properties(ProximityReporter *self, GError **error) { g_assert(PROXIMITY_REPORTER_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, PROXIMITY_REPORTER_DBUS_INTERFACE, error); } void proximity_reporter_set_property(ProximityReporter *self, const gchar *name, const GVariant *value, GError **error) { g_assert(PROXIMITY_REPORTER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, PROXIMITY_REPORTER_DBUS_INTERFACE, name, value, error); } const gchar *proximity_reporter_get_immediate_alert_level(ProximityReporter *self, GError **error) { g_assert(PROXIMITY_REPORTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, PROXIMITY_REPORTER_DBUS_INTERFACE, "ImmediateAlertLevel", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } const gchar *proximity_reporter_get_link_loss_alert_level(ProximityReporter *self, GError **error) { g_assert(PROXIMITY_REPORTER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, PROXIMITY_REPORTER_DBUS_INTERFACE, "LinkLossAlertLevel", error); if(prop == NULL) return NULL; const gchar *ret = g_variant_get_string(prop, NULL); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/proximity_reporter.h000066400000000000000000000055571315563672100247410ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __PROXIMITY_REPORTER_H #define __PROXIMITY_REPORTER_H #ifdef __cplusplus extern "C" { #endif #include #define PROXIMITY_REPORTER_DBUS_SERVICE "org.bluez" #define PROXIMITY_REPORTER_DBUS_INTERFACE "org.bluez.ProximityReporter1" /* * Type macros */ #define PROXIMITY_REPORTER_TYPE (proximity_reporter_get_type()) #define PROXIMITY_REPORTER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), PROXIMITY_REPORTER_TYPE, ProximityReporter)) #define PROXIMITY_REPORTER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), PROXIMITY_REPORTER_TYPE)) #define PROXIMITY_REPORTER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), PROXIMITY_REPORTER_TYPE, ProximityReporterClass)) #define PROXIMITY_REPORTER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), PROXIMITY_REPORTER_TYPE)) #define PROXIMITY_REPORTER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), PROXIMITY_REPORTER_TYPE, ProximityReporterClass)) typedef struct _ProximityReporter ProximityReporter; typedef struct _ProximityReporterClass ProximityReporterClass; typedef struct _ProximityReporterPrivate ProximityReporterPrivate; struct _ProximityReporter { GObject parent_instance; /*< private >*/ ProximityReporterPrivate *priv; }; struct _ProximityReporterClass { GObjectClass parent_class; }; /* used by PROXIMITY_REPORTER_TYPE */ GType proximity_reporter_get_type(void) G_GNUC_CONST; /* * Constructor */ ProximityReporter *proximity_reporter_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *proximity_reporter_get_dbus_object_path(ProximityReporter *self); GVariant *proximity_reporter_get_properties(ProximityReporter *self, GError **error); void proximity_reporter_set_property(ProximityReporter *self, const gchar *name, const GVariant *value, GError **error); const gchar *proximity_reporter_get_immediate_alert_level(ProximityReporter *self, GError **error); const gchar *proximity_reporter_get_link_loss_alert_level(ProximityReporter *self, GError **error); #ifdef __cplusplus } #endif #endif /* __PROXIMITY_REPORTER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/sim_access.c000066400000000000000000000142211315563672100230430ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "sim_access.h" #define SIM_ACCESS_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), SIM_ACCESS_TYPE, SimAccessPrivate)) struct _SimAccessPrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(SimAccess, sim_access, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _sim_access_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _sim_access_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _sim_access_create_gdbus_proxy(SimAccess *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void sim_access_dispose(GObject *gobject) { SimAccess *self = SIM_ACCESS(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(sim_access_parent_class)->dispose(gobject); } static void sim_access_finalize (GObject *gobject) { SimAccess *self = SIM_ACCESS(gobject); G_OBJECT_CLASS(sim_access_parent_class)->finalize(gobject); } static void sim_access_class_init(SimAccessClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = sim_access_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _sim_access_get_property; gobject_class->set_property = _sim_access_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "SimAccess D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void sim_access_init(SimAccess *self) { self->priv = sim_access_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _sim_access_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { SimAccess *self = SIM_ACCESS(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, sim_access_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _sim_access_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { SimAccess *self = SIM_ACCESS(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _sim_access_create_gdbus_proxy(self, SIM_ACCESS_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ SimAccess *sim_access_new(const gchar *dbus_object_path) { return g_object_new(SIM_ACCESS_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _sim_access_create_gdbus_proxy(SimAccess *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(SIM_ACCESS_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, SIM_ACCESS_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "system", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *sim_access_get_dbus_object_path(SimAccess *self) { g_assert(SIM_ACCESS_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* void Disconnect() */ void sim_access_disconnect(SimAccess *self, GError **error) { g_assert(SIM_ACCESS_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Disconnect", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } /* Properties access methods */ GVariant *sim_access_get_properties(SimAccess *self, GError **error) { g_assert(SIM_ACCESS_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, SIM_ACCESS_DBUS_INTERFACE, error); } void sim_access_set_property(SimAccess *self, const gchar *name, const GVariant *value, GError **error) { g_assert(SIM_ACCESS_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, SIM_ACCESS_DBUS_INTERFACE, name, value, error); } gboolean sim_access_get_connected(SimAccess *self, GError **error) { g_assert(SIM_ACCESS_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, SIM_ACCESS_DBUS_INTERFACE, "Connected", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/sim_access.h000066400000000000000000000047511315563672100230570ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __SIM_ACCESS_H #define __SIM_ACCESS_H #ifdef __cplusplus extern "C" { #endif #include #define SIM_ACCESS_DBUS_SERVICE "org.bluez" #define SIM_ACCESS_DBUS_INTERFACE "org.bluez.SimAccess1" /* * Type macros */ #define SIM_ACCESS_TYPE (sim_access_get_type()) #define SIM_ACCESS(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), SIM_ACCESS_TYPE, SimAccess)) #define SIM_ACCESS_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), SIM_ACCESS_TYPE)) #define SIM_ACCESS_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), SIM_ACCESS_TYPE, SimAccessClass)) #define SIM_ACCESS_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), SIM_ACCESS_TYPE)) #define SIM_ACCESS_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), SIM_ACCESS_TYPE, SimAccessClass)) typedef struct _SimAccess SimAccess; typedef struct _SimAccessClass SimAccessClass; typedef struct _SimAccessPrivate SimAccessPrivate; struct _SimAccess { GObject parent_instance; /*< private >*/ SimAccessPrivate *priv; }; struct _SimAccessClass { GObjectClass parent_class; }; /* used by SIM_ACCESS_TYPE */ GType sim_access_get_type(void) G_GNUC_CONST; /* * Constructor */ SimAccess *sim_access_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *sim_access_get_dbus_object_path(SimAccess *self); void sim_access_disconnect(SimAccess *self, GError **error); GVariant *sim_access_get_properties(SimAccess *self, GError **error); void sim_access_set_property(SimAccess *self, const gchar *name, const GVariant *value, GError **error); gboolean sim_access_get_connected(SimAccess *self, GError **error); #ifdef __cplusplus } #endif #endif /* __SIM_ACCESS_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/thermometer.c000066400000000000000000000140031315563672100232630ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "thermometer.h" #define THERMOMETER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), THERMOMETER_TYPE, ThermometerPrivate)) struct _ThermometerPrivate { GDBusProxy *proxy; Properties *properties; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(Thermometer, thermometer, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _thermometer_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _thermometer_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _thermometer_create_gdbus_proxy(Thermometer *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void thermometer_dispose(GObject *gobject) { Thermometer *self = THERMOMETER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Properties free */ g_clear_object(&self->priv->properties); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(thermometer_parent_class)->dispose(gobject); } static void thermometer_finalize (GObject *gobject) { Thermometer *self = THERMOMETER(gobject); G_OBJECT_CLASS(thermometer_parent_class)->finalize(gobject); } static void thermometer_class_init(ThermometerClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = thermometer_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _thermometer_get_property; gobject_class->set_property = _thermometer_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "Thermometer D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void thermometer_init(Thermometer *self) { self->priv = thermometer_get_instance_private (self); self->priv->proxy = NULL; self->priv->properties = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _thermometer_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { Thermometer *self = THERMOMETER(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, thermometer_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _thermometer_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { Thermometer *self = THERMOMETER(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _thermometer_create_gdbus_proxy(self, THERMOMETER_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ Thermometer *thermometer_new(const gchar *dbus_object_path) { return g_object_new(THERMOMETER_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _thermometer_create_gdbus_proxy(Thermometer *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(THERMOMETER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, THERMOMETER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; self->priv->properties = g_object_new(PROPERTIES_TYPE, "DBusType", "system", "DBusServiceName", dbus_service_name, "DBusObjectPath", dbus_object_path, NULL); g_assert(self->priv->properties != NULL); } /* Methods */ /* Get DBus object path */ const gchar *thermometer_get_dbus_object_path(Thermometer *self) { g_assert(THERMOMETER_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } /* Properties access methods */ GVariant *thermometer_get_properties(Thermometer *self, GError **error) { g_assert(THERMOMETER_IS(self)); g_assert(self->priv->properties != NULL); return properties_get_all(self->priv->properties, THERMOMETER_DBUS_INTERFACE, error); } void thermometer_set_property(Thermometer *self, const gchar *name, const GVariant *value, GError **error) { g_assert(THERMOMETER_IS(self)); g_assert(self->priv->properties != NULL); properties_set(self->priv->properties, THERMOMETER_DBUS_INTERFACE, name, value, error); } gboolean thermometer_get_intermediate(Thermometer *self, GError **error) { g_assert(THERMOMETER_IS(self)); g_assert(self->priv->properties != NULL); GVariant *prop = properties_get(self->priv->properties, THERMOMETER_DBUS_INTERFACE, "Intermediate", error); if(prop == NULL) return FALSE; gboolean ret = g_variant_get_boolean(prop); g_variant_unref(prop); return ret; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/thermometer.h000066400000000000000000000047521315563672100233020ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __THERMOMETER_H #define __THERMOMETER_H #ifdef __cplusplus extern "C" { #endif #include #define THERMOMETER_DBUS_SERVICE "org.bluez" #define THERMOMETER_DBUS_INTERFACE "org.bluez.Thermometer1" /* * Type macros */ #define THERMOMETER_TYPE (thermometer_get_type()) #define THERMOMETER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), THERMOMETER_TYPE, Thermometer)) #define THERMOMETER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), THERMOMETER_TYPE)) #define THERMOMETER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), THERMOMETER_TYPE, ThermometerClass)) #define THERMOMETER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), THERMOMETER_TYPE)) #define THERMOMETER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), THERMOMETER_TYPE, ThermometerClass)) typedef struct _Thermometer Thermometer; typedef struct _ThermometerClass ThermometerClass; typedef struct _ThermometerPrivate ThermometerPrivate; struct _Thermometer { GObject parent_instance; /*< private >*/ ThermometerPrivate *priv; }; struct _ThermometerClass { GObjectClass parent_class; }; /* used by THERMOMETER_TYPE */ GType thermometer_get_type(void) G_GNUC_CONST; /* * Constructor */ Thermometer *thermometer_new(const gchar *dbus_object_path); /* * Method definitions */ const gchar *thermometer_get_dbus_object_path(Thermometer *self); GVariant *thermometer_get_properties(Thermometer *self, GError **error); void thermometer_set_property(Thermometer *self, const gchar *name, const GVariant *value, GError **error); gboolean thermometer_get_intermediate(Thermometer *self, GError **error); #ifdef __cplusplus } #endif #endif /* __THERMOMETER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/thermometer_manager.c000066400000000000000000000122061315563672100247600ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "../dbus-common.h" #include "../properties.h" #include "thermometer_manager.h" #define THERMOMETER_MANAGER_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), THERMOMETER_MANAGER_TYPE, ThermometerManagerPrivate)) struct _ThermometerManagerPrivate { GDBusProxy *proxy; gchar *object_path; }; G_DEFINE_TYPE_WITH_PRIVATE(ThermometerManager, thermometer_manager, G_TYPE_OBJECT); enum { PROP_0, PROP_DBUS_OBJECT_PATH /* readwrite, construct only */ }; static void _thermometer_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _thermometer_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _thermometer_manager_create_gdbus_proxy(ThermometerManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error); static void thermometer_manager_dispose(GObject *gobject) { ThermometerManager *self = THERMOMETER_MANAGER(gobject); /* Proxy free */ g_clear_object (&self->priv->proxy); /* Object path free */ g_free(self->priv->object_path); /* Chain up to the parent class */ G_OBJECT_CLASS(thermometer_manager_parent_class)->dispose(gobject); } static void thermometer_manager_finalize (GObject *gobject) { ThermometerManager *self = THERMOMETER_MANAGER(gobject); G_OBJECT_CLASS(thermometer_manager_parent_class)->finalize(gobject); } static void thermometer_manager_class_init(ThermometerManagerClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = thermometer_manager_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _thermometer_manager_get_property; gobject_class->set_property = _thermometer_manager_set_property; /* object DBusObjectPath [readwrite, construct only] */ pspec = g_param_spec_string("DBusObjectPath", "dbus_object_path", "ThermometerManager D-Bus object path", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_DBUS_OBJECT_PATH, pspec); if (pspec) g_param_spec_unref(pspec); } static void thermometer_manager_init(ThermometerManager *self) { self->priv = thermometer_manager_get_instance_private (self); self->priv->proxy = NULL; self->priv->object_path = NULL; g_assert(system_conn != NULL); } static void _thermometer_manager_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ThermometerManager *self = THERMOMETER_MANAGER(object); switch (property_id) { case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, thermometer_manager_get_dbus_object_path(self)); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _thermometer_manager_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ThermometerManager *self = THERMOMETER_MANAGER(object); GError *error = NULL; switch (property_id) { case PROP_DBUS_OBJECT_PATH: self->priv->object_path = g_value_dup_string(value); _thermometer_manager_create_gdbus_proxy(self, THERMOMETER_MANAGER_DBUS_SERVICE, self->priv->object_path, &error); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } if (error != NULL) g_critical("%s", error->message); g_assert(error == NULL); } /* Constructor */ ThermometerManager *thermometer_manager_new(const gchar *dbus_object_path) { return g_object_new(THERMOMETER_MANAGER_TYPE, "DBusObjectPath", dbus_object_path, NULL); } /* Private DBus proxy creation */ static void _thermometer_manager_create_gdbus_proxy(ThermometerManager *self, const gchar *dbus_service_name, const gchar *dbus_object_path, GError **error) { g_assert(THERMOMETER_MANAGER_IS(self)); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, THERMOMETER_MANAGER_DBUS_INTERFACE, NULL, error); if(self->priv->proxy == NULL) return; } /* Methods */ /* Get DBus object path */ const gchar *thermometer_manager_get_dbus_object_path(ThermometerManager *self) { g_assert(THERMOMETER_MANAGER_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/bluez/thermometer_manager.h000066400000000000000000000047341315563672100247740ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __THERMOMETER_MANAGER_H #define __THERMOMETER_MANAGER_H #ifdef __cplusplus extern "C" { #endif #include #define THERMOMETER_MANAGER_DBUS_SERVICE "org.bluez" #define THERMOMETER_MANAGER_DBUS_INTERFACE "org.bluez.ThermometerManager1" /* * Type macros */ #define THERMOMETER_MANAGER_TYPE (thermometer_manager_get_type()) #define THERMOMETER_MANAGER(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), THERMOMETER_MANAGER_TYPE, ThermometerManager)) #define THERMOMETER_MANAGER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), THERMOMETER_MANAGER_TYPE)) #define THERMOMETER_MANAGER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), THERMOMETER_MANAGER_TYPE, ThermometerManagerClass)) #define THERMOMETER_MANAGER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), THERMOMETER_MANAGER_TYPE)) #define THERMOMETER_MANAGER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), THERMOMETER_MANAGER_TYPE, ThermometerManagerClass)) typedef struct _ThermometerManager ThermometerManager; typedef struct _ThermometerManagerClass ThermometerManagerClass; typedef struct _ThermometerManagerPrivate ThermometerManagerPrivate; struct _ThermometerManager { GObject parent_instance; /*< private >*/ ThermometerManagerPrivate *priv; }; struct _ThermometerManagerClass { GObjectClass parent_class; }; /* used by THERMOMETER_MANAGER_TYPE */ GType thermometer_manager_get_type(void) G_GNUC_CONST; /* * Constructor */ ThermometerManager *thermometer_manager_new(const gchar *dbus_object_path); const gchar *thermometer_manager_get_dbus_object_path(ThermometerManager *self); #ifdef __cplusplus } #endif #endif /* __THERMOMETER_MANAGER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/dbus-common.c000066400000000000000000000020121315563672100220270ustar00rootroot00000000000000#ifdef HAVE_CONFIG_H #include #endif #include #include "bluez-api.h" #include "dbus-common.h" GDBusConnection *session_conn = NULL; GDBusConnection *system_conn = NULL; static gboolean dbus_initialized = FALSE; void dbus_init() { dbus_initialized = TRUE; } gboolean dbus_session_connect(GError **error) { g_assert(dbus_initialized == TRUE); session_conn = g_bus_get_sync(G_BUS_TYPE_SESSION, NULL, error); if (!session_conn) { return FALSE; } return TRUE; } void dbus_session_disconnect() { g_object_unref(session_conn); } gboolean dbus_system_connect(GError **error) { g_assert(dbus_initialized == TRUE); system_conn = g_bus_get_sync(G_BUS_TYPE_SYSTEM, NULL, error); if (!system_conn) { return FALSE; } return TRUE; } void dbus_system_disconnect() { g_object_unref(system_conn); } void dbus_disconnect() { if (system_conn) dbus_system_disconnect(); if (session_conn) dbus_session_disconnect(); } bluez-tools-2.0~20170911.0.7cb788c/src/lib/dbus-common.h000066400000000000000000000006671315563672100220520ustar00rootroot00000000000000#ifndef DBUS_COMMON_H #define DBUS_COMMON_H #ifdef __cplusplus extern "C" { #endif #include extern GDBusConnection *session_conn; extern GDBusConnection *system_conn; void dbus_init(); gboolean dbus_session_connect(GError **error); void dbus_session_disconnect(); gboolean dbus_system_connect(GError **error); void dbus_system_disconnect(); void dbus_disconnect(); #ifdef __cplusplus } #endif #endif /* DBUS_COMMON_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/helpers.c000066400000000000000000000362061315563672100212620ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include #include #include #include "dbus-common.h" #include "helpers.h" /* UUID Name lookup table */ typedef struct { gchar *uuid; gchar *name; gchar *alt_name; } uuid_name_lookup_table_t; static uuid_name_lookup_table_t uuid_name_lookup_table[] = { {"00001000-0000-1000-8000-00805F9B34FB", "ServiceDiscoveryServer", NULL}, {"00001001-0000-1000-8000-00805F9B34FB", "BrowseGroupDescriptor", NULL}, {"00001002-0000-1000-8000-00805F9B34FB", "PublicBrowseGroup", NULL}, {"00001101-0000-1000-8000-00805F9B34FB", "SerialPort", "Serial"}, {"00001102-0000-1000-8000-00805F9B34FB", "LANAccessUsingPPP", NULL}, {"00001103-0000-1000-8000-00805F9B34FB", "DialupNetworking", "DUN"}, {"00001104-0000-1000-8000-00805F9B34FB", "IrMCSync", NULL}, {"00001105-0000-1000-8000-00805F9B34FB", "OBEXObjectPush", NULL}, {"00001106-0000-1000-8000-00805F9B34FB", "OBEXFileTransfer", NULL}, {"00001107-0000-1000-8000-00805F9B34FB", "IrMCSyncCommand", NULL}, {"00001108-0000-1000-8000-00805F9B34FB", "Headset", NULL}, {"00001109-0000-1000-8000-00805F9B34FB", "CordlessTelephony", NULL}, {"0000110A-0000-1000-8000-00805F9B34FB", "AudioSource", NULL}, {"0000110B-0000-1000-8000-00805F9B34FB", "AudioSink", NULL}, {"0000110C-0000-1000-8000-00805F9B34FB", "AVRemoteControlTarget", NULL}, {"0000110D-0000-1000-8000-00805F9B34FB", "AdvancedAudioDistribution", "A2DP"}, {"0000110E-0000-1000-8000-00805F9B34FB", "AVRemoteControl", NULL}, {"0000110F-0000-1000-8000-00805F9B34FB", "VideoConferencing", NULL}, {"00001110-0000-1000-8000-00805F9B34FB", "Intercom", NULL}, {"00001111-0000-1000-8000-00805F9B34FB", "Fax", NULL}, {"00001112-0000-1000-8000-00805F9B34FB", "HeadsetAudioGateway", NULL}, {"00001113-0000-1000-8000-00805F9B34FB", "WAP", NULL}, {"00001114-0000-1000-8000-00805F9B34FB", "WAPClient", NULL}, {"00001115-0000-1000-8000-00805F9B34FB", "PANU", NULL}, {"00001116-0000-1000-8000-00805F9B34FB", "NAP", NULL}, {"00001117-0000-1000-8000-00805F9B34FB", "GN", NULL}, {"00001118-0000-1000-8000-00805F9B34FB", "DirectPrinting", NULL}, {"00001119-0000-1000-8000-00805F9B34FB", "ReferencePrinting", NULL}, {"0000111A-0000-1000-8000-00805F9B34FB", "Imaging", NULL}, {"0000111B-0000-1000-8000-00805F9B34FB", "ImagingResponder", NULL}, {"0000111C-0000-1000-8000-00805F9B34FB", "ImagingAutomaticArchive", NULL}, {"0000111D-0000-1000-8000-00805F9B34FB", "ImagingReferenceObjects", NULL}, {"0000111E-0000-1000-8000-00805F9B34FB", "Handsfree", NULL}, {"0000111F-0000-1000-8000-00805F9B34FB", "HandsfreeAudioGateway", NULL}, {"00001120-0000-1000-8000-00805F9B34FB", "DirectPrintingReferenceObjects", NULL}, {"00001121-0000-1000-8000-00805F9B34FB", "ReflectedUI", NULL}, {"00001122-0000-1000-8000-00805F9B34FB", "BasicPringing", NULL}, {"00001123-0000-1000-8000-00805F9B34FB", "PrintingStatus", NULL}, {"00001124-0000-1000-8000-00805F9B34FB", "HumanInterfaceDevice", "HID"}, {"00001125-0000-1000-8000-00805F9B34FB", "HardcopyCableReplacement", NULL}, {"00001126-0000-1000-8000-00805F9B34FB", "HCRPrint", NULL}, {"00001127-0000-1000-8000-00805F9B34FB", "HCRScan", NULL}, {"00001128-0000-1000-8000-00805F9B34FB", "CommonISDNAccess", NULL}, {"00001129-0000-1000-8000-00805F9B34FB", "VideoConferencingGW", NULL}, {"0000112A-0000-1000-8000-00805F9B34FB", "UDIMT", NULL}, {"0000112B-0000-1000-8000-00805F9B34FB", "UDITA", NULL}, {"0000112C-0000-1000-8000-00805F9B34FB", "AudioVideo", NULL}, {"00001200-0000-1000-8000-00805F9B34FB", "PnPInformation", NULL}, {"00001201-0000-1000-8000-00805F9B34FB", "GenericNetworking", NULL}, {"00001202-0000-1000-8000-00805F9B34FB", "GenericFileTransfer", NULL}, {"00001203-0000-1000-8000-00805F9B34FB", "GenericAudio", NULL}, {"00001204-0000-1000-8000-00805F9B34FB", "GenericTelephony", NULL}, {"00001205-0000-1000-8000-00805F9B34FB", "UPnP", NULL}, {"00001206-0000-1000-8000-00805F9B34FB", "UPnPIp", NULL}, {"00001300-0000-1000-8000-00805F9B34FB", "ESdpUPnPIpPan", NULL}, {"00001301-0000-1000-8000-00805F9B34FB", "ESdpUPnPIpLap", NULL}, {"00001302-0000-1000-8000-00805F9B34FB", "EdpUPnpIpL2CAP", NULL}, // Custom: {"0000112F-0000-1000-8000-00805F9B34FB", "PhoneBookAccess", NULL}, {"831C4071-7BC8-4A9C-A01C-15DF25A4ADBC", "ActiveSync", NULL}, }; #define UUID_NAME_LOOKUP_TABLE_SIZE \ (sizeof(uuid_name_lookup_table)/sizeof(uuid_name_lookup_table_t)) const gchar *uuid2name(const gchar *uuid) { if (uuid == NULL || strlen(uuid) == 0) return NULL; for (int i = 0; i < UUID_NAME_LOOKUP_TABLE_SIZE; i++) { if (g_ascii_strcasecmp(uuid_name_lookup_table[i].uuid, uuid) == 0) return uuid_name_lookup_table[i].name; } return uuid; } const gchar *name2uuid(const gchar *name) { if (name == NULL || strlen(name) == 0) return NULL; for (int i = 0; i < UUID_NAME_LOOKUP_TABLE_SIZE; i++) { if ( g_ascii_strcasecmp(uuid_name_lookup_table[i].name, name) == 0 || (uuid_name_lookup_table[i].alt_name && g_ascii_strcasecmp(uuid_name_lookup_table[i].alt_name, name) == 0) ) return uuid_name_lookup_table[i].uuid; } return name; } int xtoi(const gchar *str) { int i = 0; sscanf(str, "0x%x", &i); return i; } Adapter *find_adapter(const gchar *name, GError **error) { gchar *adapter_path = NULL; Adapter *adapter = NULL; Manager *manager = g_object_new(MANAGER_TYPE, NULL); // If name is null or empty - return default adapter if (name == NULL || strlen(name) == 0) { adapter_path = (gchar *) manager_default_adapter(manager, error); if (adapter_path) { // adapter = g_object_new(ADAPTER_TYPE, "DBusObjectPath", adapter_path, NULL); adapter = adapter_new(adapter_path); } } else { // Try to find by id adapter_path = (gchar *) manager_find_adapter(manager, name, error); // Found if (adapter_path) { // adapter = g_object_new(ADAPTER_TYPE, "DBusObjectPath", adapter_path, NULL); adapter = adapter_new(adapter_path); } else { // Try to find by name const GPtrArray *adapters_list = manager_get_adapters(manager); g_assert(adapters_list != NULL); for (int i = 0; i < adapters_list->len; i++) { adapter_path = g_ptr_array_index(adapters_list, i); // adapter = g_object_new(ADAPTER_TYPE, "DBusObjectPath", adapter_path, NULL); adapter = adapter_new(adapter_path); adapter_path = NULL; if (g_strcmp0(name, adapter_get_name(adapter, error)) == 0) { if (error) { g_error_free(*error); *error = NULL; } break; } g_object_unref(adapter); adapter = NULL; } } } g_object_unref(manager); if (adapter_path) g_free(adapter_path); return adapter; } Device *find_device(Adapter *adapter, const gchar *name, GError **error) { g_assert(adapter != NULL && ADAPTER_IS(adapter)); g_assert(name != NULL && strlen(name) > 0); Device *device = NULL; Manager *manager = g_object_new(MANAGER_TYPE, NULL); GVariant *objects = manager_get_managed_objects(manager, error); g_clear_object(&manager); if(!objects) { return NULL; } const gchar *object_path; GVariant *ifaces_and_properties; GVariantIter i; g_variant_iter_init(&i, objects); while (g_variant_iter_next(&i, "{&o@a{sa{sv}}}", &object_path, &ifaces_and_properties) && device == NULL) { GVariant *properties = NULL; if(g_variant_lookup(ifaces_and_properties, DEVICE_DBUS_INTERFACE, "@a{sv}", &properties)) { gchar *adapter_path = NULL; if(g_variant_lookup(properties, "Adapter", "o", &adapter_path)) { if(g_strcmp0(adapter_path, adapter_get_dbus_object_path(adapter)) == 0) { // Now check if this is the device we are looking for. // Try to find by MAC gchar *address = NULL; if(g_variant_lookup(properties, "Address", "s", &address)) { if(g_strcmp0(g_ascii_strdown(address, -1), g_ascii_strdown(name, -1)) == 0) { device = device_new(object_path); } g_free(address); } // Try to find by name or alias if(!device) { gchar *device_name = NULL; gchar *device_alias = NULL; g_variant_lookup(properties, "Name", "s", &device_name); g_variant_lookup(properties, "Alias", "s", &device_alias); if (g_strcmp0(name, device_name) == 0 || g_strcmp0(name, device_alias) == 0) { device = device_new(object_path); } g_free(device_alias); g_free(device_name); } } g_free(adapter_path); } g_variant_unref(properties); } g_variant_unref(ifaces_and_properties); } g_variant_unref(objects); return device; } gboolean intf_supported(const gchar *dbus_service_name, const gchar *dbus_object_path, const gchar *intf_name) { g_assert(dbus_service_name != NULL && strlen(dbus_service_name) > 0); g_assert(dbus_object_path != NULL && strlen(dbus_object_path) > 0); g_assert(intf_name != NULL && strlen(intf_name) > 0); gboolean supported = FALSE; GDBusConnection *conn = NULL; if (g_strcmp0(dbus_service_name, BLUEZ_DBUS_SERVICE_NAME) == 0) { conn = system_conn; } else if (g_strcmp0(dbus_service_name, BLUEZ_OBEX_DBUS_SERVICE_NAME) == 0) { conn = session_conn; } else { return FALSE; } g_assert(conn != NULL); gchar *check_intf_regex_str = g_strconcat("", NULL); /* Getting introspection XML */ GError *error = NULL; GDBusProxy *introspection_proxy = g_dbus_proxy_new_sync(conn, G_DBUS_PROXY_FLAGS_NONE, NULL, dbus_service_name, dbus_object_path, "org.freedesktop.DBus.Introspectable", NULL, &error); g_assert(introspection_proxy != NULL); GVariant *introspection_ret = g_dbus_proxy_call_sync(introspection_proxy, "Introspect", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, &error); gchar *introspection_xml = NULL; if (!introspection_ret) { #if 0 g_critical("%s", error->message); #else g_error_free(error); error = NULL; introspection_xml = g_strdup("null"); #endif } else { introspection_xml = (gchar *) g_variant_get_string(g_variant_get_child_value(introspection_ret, 0), NULL); } g_assert(error == NULL); if (g_regex_match_simple(check_intf_regex_str, introspection_xml, 0, 0)) { supported = TRUE; } g_free(check_intf_regex_str); g_free(introspection_xml); if(introspection_ret) g_variant_unref(introspection_ret); g_object_unref(introspection_proxy); return supported; } gboolean is_file(const gchar *filename, GError **error) { g_assert(filename != NULL && strlen(filename) > 0); struct stat buf; if (stat(filename, &buf) != 0) { if (error) { *error = g_error_new(g_quark_from_string("bluez-tools"), 1, "%s: %s", g_strdup(filename), strerror(errno)); } return FALSE; } if (!S_ISREG(buf.st_mode)) { if (error) { *error = g_error_new(g_quark_from_string("bluez-tools"), 2, "%s: Invalid file", g_strdup(filename)); } return FALSE; } return TRUE; } gboolean is_dir(const gchar *dirname, GError **error) { g_assert(dirname != NULL && strlen(dirname) > 0); struct stat buf; if (stat(dirname, &buf) != 0) { if (error) { *error = g_error_new(g_quark_from_string("bluez-tools"), 1, "%s: %s", g_strdup(dirname), strerror(errno)); } return FALSE; } if (!S_ISDIR(buf.st_mode)) { if (error) { *error = g_error_new(g_quark_from_string("bluez-tools"), 2, "%s: Invalid directory", g_strdup(dirname)); } return FALSE; } return TRUE; } gboolean read_access(const gchar *path, GError **error) { if(g_access(path, F_OK) != 0) { if (error) { *error = g_error_new(g_quark_from_string("bluez-tools"), 3, "%s: No such file or directory", g_strdup(path)); } return FALSE; } if(g_access(path, R_OK | F_OK) != 0) { if (error) { *error = g_error_new(g_quark_from_string("bluez-tools"), 4, "%s: Read permission denied", g_strdup(path)); } return FALSE; } return TRUE; } gboolean write_access(const gchar *path, GError **error) { if(g_access(path, F_OK) != 0) { if (error) { *error = g_error_new(g_quark_from_string("bluez-tools"), 3, "%s: No such file or directory", g_strdup(path)); } return FALSE; } if(g_access(path, W_OK | F_OK) != 0) { if (error) { *error = g_error_new(g_quark_from_string("bluez-tools"), 5, "%s: Write permission denied", g_strdup(path)); } return FALSE; } return TRUE; } gchar *get_absolute_path(const gchar *path) { if (g_path_is_absolute(path)) { return g_strdup(path); } gchar *current_dir = g_get_current_dir(); gchar *abs_path = g_build_filename(current_dir, path, NULL); g_free(current_dir); return abs_path; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/helpers.h000066400000000000000000000041021315563672100212550ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __HELPERS_H #define __HELPERS_H #include #include #include #include "bluez-api.h" /* DBus helpers */ gboolean intf_supported(const gchar *dbus_service_name, const gchar *dbus_object_path, const gchar *intf_name); /* BlueZ helpers */ Adapter *find_adapter(const gchar *name, GError **error); Device *find_device(Adapter *adapter, const gchar *name, GError **error); /* Others helpers */ #define exit_if_error(error) G_STMT_START{ \ if (error) { \ g_printerr("%s: %s\n", (error->domain == G_DBUS_ERROR && g_dbus_error_get_remote_error(error) != NULL && strlen(g_dbus_error_get_remote_error(error)) ? g_dbus_error_get_remote_error(error) : "Error"), error->message); \ exit(EXIT_FAILURE); \ }; }G_STMT_END /* Convert hex string to int */ int xtoi(const gchar *str); /* UUID converters */ const gchar *uuid2name(const gchar *uuid); const gchar *name2uuid(const gchar *name); /* FS helpers */ gboolean is_file(const gchar *filename, GError **error); gboolean is_dir(const gchar *dirname, GError **error); gboolean read_access(const gchar *path, GError **error); gboolean write_access(const gchar *path, GError **error); gchar *get_absolute_path(const gchar *path); #endif /* __HELPERS_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/manager.c000066400000000000000000000207061315563672100212300ustar00rootroot00000000000000#include #include "bluez-api.h" #include "dbus-common.h" #include "manager.h" struct _ManagerPrivate { GDBusProxy *proxy; }; G_DEFINE_TYPE_WITH_PRIVATE(Manager, manager, G_TYPE_OBJECT) static void manager_dispose (GObject *gobject) { Manager *self = MANAGER (gobject); /* In dispose(), you are supposed to free all types referenced from this * object which might themselves hold a reference to self. Generally, * the most simple solution is to unref all members on which you own a * reference. */ /* dispose() might be called multiple times, so we must guard against * calling g_object_unref() on an invalid GObject by setting the member * NULL; g_clear_object() does this for us, atomically. */ // g_clear_object (&self->priv->an_object); g_clear_object (&self->priv->proxy); /* Always chain up to the parent class; there is no need to check if * the parent class implements the dispose() virtual function: it is * always guaranteed to do so */ G_OBJECT_CLASS (manager_parent_class)->dispose (gobject); } static void manager_finalize (GObject *gobject) { Manager *self = MANAGER(gobject); // g_free(self->priv->a_string); /* Always chain up to the parent class; as with dispose(), finalize() * is guaranteed to exist on the parent's class virtual function table */ G_OBJECT_CLASS (manager_parent_class)->finalize (gobject); } static void manager_class_init(ManagerClass *klass) { } static void manager_init(Manager *self) { self->priv = manager_get_instance_private(self); GError *error = NULL; g_assert(system_conn != NULL); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, BLUEZ_DBUS_SERVICE_NAME, MANAGER_DBUS_PATH, MANAGER_DBUS_INTERFACE, NULL, &error); if (self->priv->proxy == NULL) { g_critical("%s", error->message); } g_assert(error == NULL); } Manager *manager_new() { return g_object_new(MANAGER_TYPE, NULL); } GVariant *manager_get_managed_objects(Manager *self, GError **error) { g_assert(MANAGER_IS(self)); GVariant *retVal = NULL; retVal = g_dbus_proxy_call_sync(self->priv->proxy, "GetManagedObjects", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (retVal != NULL) retVal = g_variant_get_child_value(retVal, 0); return retVal; } const gchar *manager_default_adapter(Manager *self, GError **error) { g_assert(MANAGER_IS(self)); GVariant *objects = NULL; objects = manager_get_managed_objects(self, error); if (objects == NULL) return NULL; const gchar *object_path; GVariant *ifaces_and_properties; GVariantIter i; g_variant_iter_init(&i, objects); while (g_variant_iter_next(&i, "{&o@a{sa{sv}}}", &object_path, &ifaces_and_properties)) { const gchar *interface_name; GVariant *properties; GVariantIter ii; g_variant_iter_init(&ii, ifaces_and_properties); while (g_variant_iter_next(&ii, "{&s@a{sv}}", &interface_name, &properties)) { if (g_strstr_len(g_ascii_strdown(interface_name, -1), -1, "adapter")) { const gchar *retVal = g_strdup(object_path); g_variant_unref(properties); g_variant_unref(ifaces_and_properties); g_variant_unref(objects); return retVal; } g_variant_unref(properties); } g_variant_unref(ifaces_and_properties); } g_variant_unref(objects); return NULL; } const gchar *manager_find_adapter(Manager *self, const gchar *pattern, GError **error) { g_assert(MANAGER_IS(self)); GVariant *objects = NULL; objects = manager_get_managed_objects(self, error); if (objects == NULL) return NULL; const gchar *object_path; GVariant *ifaces_and_properties; GVariantIter i; g_variant_iter_init(&i, objects); while (g_variant_iter_next(&i, "{&o@a{sa{sv}}}", &object_path, &ifaces_and_properties)) { const gchar *interface_name; GVariant *properties; GVariantIter ii; g_variant_iter_init(&ii, ifaces_and_properties); while (g_variant_iter_next(&ii, "{&s@a{sv}}", &interface_name, &properties)) { if (g_strstr_len(g_ascii_strdown(interface_name, -1), -1, "adapter")) { const gchar *object_base_name = g_path_get_basename(object_path); if (g_strstr_len(g_ascii_strdown(object_base_name, -1), -1, g_ascii_strdown(pattern, -1))) { const gchar *retVal = g_strdup(object_path); g_variant_unref(properties); g_variant_unref(ifaces_and_properties); g_variant_unref(objects); return retVal; } const gchar *address = g_variant_get_string(g_variant_lookup_value(properties, "Address", NULL), NULL); if (g_strstr_len(g_ascii_strdown(address, -1), -1, g_ascii_strdown(pattern, -1))) { gchar *retVal = g_strdup(object_path); g_variant_unref(properties); g_variant_unref(ifaces_and_properties); g_variant_unref(objects); return retVal; } } g_variant_unref(properties); } g_variant_unref(ifaces_and_properties); } g_variant_unref(objects); return NULL; } GPtrArray *manager_get_adapters(Manager *self) { g_assert(MANAGER_IS(self)); GVariant *objects = NULL; GError *error = NULL; objects = manager_get_managed_objects(self, &error); if (objects == NULL) { g_critical("%s", error->message); g_error_free(error); return NULL; } GPtrArray *adapter_array = g_ptr_array_new(); const gchar *object_path; GVariant *ifaces_and_properties; GVariantIter i; g_variant_iter_init(&i, objects); while (g_variant_iter_next(&i, "{&o@a{sa{sv}}}", &object_path, &ifaces_and_properties)) { const gchar *interface_name; GVariant *properties; GVariantIter ii; g_variant_iter_init(&ii, ifaces_and_properties); while (g_variant_iter_next(&ii, "{&s@a{sv}}", &interface_name, &properties)) { if (g_strstr_len(g_ascii_strdown(interface_name, -1), -1, "adapter")) g_ptr_array_add(adapter_array, (gpointer) g_strdup(object_path)); g_variant_unref(properties); } g_variant_unref(ifaces_and_properties); } g_variant_unref(objects); return adapter_array; } const gchar **manager_get_devices(Manager *self, const gchar *adapter_pattern) { g_assert(MANAGER_IS(self)); GVariant *objects = NULL; GError *error = NULL; objects = manager_get_managed_objects(self, &error); if (objects == NULL) { g_critical("%s", error->message); g_error_free(error); return NULL; } GRegex *adapter_regex = g_regex_new(adapter_pattern, 0, 0, &error); if (adapter_regex == NULL) { g_critical("%s", error->message); g_error_free(error); } GPtrArray *device_array = g_ptr_array_new(); const gchar *object_path; GVariant *ifaces_and_properties; GVariantIter i; g_variant_iter_init(&i, objects); while (g_variant_iter_next(&i, "{&o@a{sa{sv}}}", &object_path, &ifaces_and_properties)) { const gchar *interface_name; GVariant *properties; GVariantIter ii; g_variant_iter_init(&ii, ifaces_and_properties); while (g_variant_iter_next(&ii, "{&s@a{sv}}", &interface_name, &properties)) { if (g_strcmp0(interface_name, "org.bluez.Device1") == 0) { const gchar *adapter_prop = g_variant_get_string(g_variant_lookup_value(properties, "Adapter", G_VARIANT_TYPE_OBJECT_PATH), NULL); if(g_regex_match(adapter_regex, adapter_prop, 0, NULL)) g_ptr_array_add(device_array, (gpointer) g_strdup(object_path)); } g_variant_unref(properties); } g_variant_unref(ifaces_and_properties); } g_variant_unref(objects); g_regex_unref(adapter_regex); if(device_array->len > 0) { // Top it off with a NULL pointer g_ptr_array_add(device_array, (gpointer) NULL); return (const gchar**) g_ptr_array_free(device_array, FALSE); } else return NULL; }bluez-tools-2.0~20170911.0.7cb788c/src/lib/manager.h000066400000000000000000000035731315563672100212400ustar00rootroot00000000000000#ifndef MANAGER_H #define MANAGER_H #ifdef __cplusplus extern "C" { #endif #include /* * Potentially, include other headers on which this header depends. */ /* * Type macros. */ #define MANAGER_TYPE (manager_get_type ()) #define MANAGER(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), MANAGER_TYPE, Manager)) #define MANAGER_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), MANAGER_TYPE)) #define MANAGER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), MANAGER_TYPE, ManagerClass)) #define MANAGER_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), MANAGER_TYPE)) #define MANAGER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), MANAGER_TYPE, ManagerClass)) #define MANAGER_DBUS_PATH "/" #define MANAGER_DBUS_INTERFACE "org.freedesktop.DBus.ObjectManager" typedef struct _Manager Manager; typedef struct _ManagerPrivate ManagerPrivate; typedef struct _ManagerClass ManagerClass; struct _Manager { /* Parent instance structure */ GObject parent_instance; /* instance members */ ManagerPrivate *priv; }; struct _ManagerClass { /* Parent class structure */ GObjectClass parent_class; /* class members */ }; /* used by MANAGER_TYPE */ GType manager_get_type(void); /* * Constructor */ Manager *manager_new(); /* * Method definitions. */ GVariant *manager_get_managed_objects(Manager *self, GError **error); const gchar *manager_default_adapter(Manager *self, GError **error); const gchar *manager_find_adapter(Manager *self, const gchar *pattern, GError **error); GPtrArray *manager_get_adapters(Manager *self); const gchar **manager_get_devices(Manager *self, const gchar *adapter_pattern); #ifdef __cplusplus } #endif #endif /* MANAGER_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/obex_agent.c000066400000000000000000000270601315563672100217310ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include "dbus-common.h" #include "helpers.h" #include "properties.h" #include "obex_agent.h" #include "bluez/obex/obex_transfer.h" #define OBEX_AGENT_GET_PRIVATE(obj) (G_TYPE_INSTANCE_GET_PRIVATE((obj), OBEX_AGENT_TYPE, ObexAgentPrivate)) struct _ObexAgentPrivate { gchar *root_folder; gboolean auto_accept; gchar *current_name; guint registration_id; void (*agent_released_callback)(ObexAgent *, gpointer); gpointer user_data; void (*agent_approved_callback)(ObexAgent *, const gchar *, const gchar *, const guint64, gpointer); gpointer approved_user_data; }; G_DEFINE_TYPE_WITH_PRIVATE(ObexAgent, obex_agent, G_TYPE_OBJECT); enum { PROP_0, PROP_ROOT_FOLDER, /* readwrite, construct only */ PROP_AUTO_ACCPET, /* readwrite, construct only */ }; static const gchar *_obex_agent_introspect_xml = "\n\t\n\t\t\n\t\t\n\t\t\n\t\t\t\n\t\t\t\n\t\t\n\t\t\n\t\t\n\t\n\n"; /* Client API */ static gboolean _update_progress = FALSE; static void _obex_agent_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec); static void _obex_agent_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec); static void _obex_agent_method_call_func(GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *method_name, GVariant *parameters, GDBusMethodInvocation *invocation, gpointer user_data); static void _obex_agent_g_destroy_notify(gpointer data); static void obex_agent_dispose(GObject *gobject) { ObexAgent *self = OBEX_AGENT(gobject); if(self->priv->registration_id) g_dbus_connection_unregister_object(session_conn, self->priv->registration_id); /* Root folder free */ g_free(self->priv->root_folder); /* callback free */ if(self->priv->agent_released_callback) self->priv->agent_released_callback = NULL; /* user data free */ if(self->priv->user_data) self->priv->user_data = NULL; /* callback free */ if(self->priv->agent_approved_callback) self->priv->agent_approved_callback = NULL; /* user data free */ if(self->priv->approved_user_data) self->priv->approved_user_data = NULL; /* Chain up to the parent class */ G_OBJECT_CLASS(obex_agent_parent_class)->dispose(gobject); } static void obex_agent_finalize (GObject *gobject) { ObexAgent *self = OBEX_AGENT(gobject); G_OBJECT_CLASS(obex_agent_parent_class)->finalize(gobject); } static void obex_agent_class_init(ObexAgentClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS(klass); gobject_class->dispose = obex_agent_dispose; /* Properties registration */ GParamSpec *pspec = NULL; gobject_class->get_property = _obex_agent_get_property; gobject_class->set_property = _obex_agent_set_property; /* string RootFolder [readwrite, construct only] */ pspec = g_param_spec_string("RootFolder", "root_folder", "Root folder location", NULL, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_ROOT_FOLDER, pspec); if (pspec) { g_param_spec_unref(pspec); pspec = NULL; } /* boolean AutoAccept [readwrite, construct only] */ pspec = g_param_spec_boolean("AutoAccept", "auto_accept", "Automatically accept incoming files", FALSE, G_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY); g_object_class_install_property(gobject_class, PROP_AUTO_ACCPET, pspec); if (pspec) g_param_spec_unref(pspec); } static void obex_agent_init(ObexAgent *self) { self->priv = obex_agent_get_instance_private(self); g_assert(session_conn != NULL); self->priv->registration_id = 0; self->priv->root_folder = NULL; self->priv->agent_released_callback = NULL; self->priv->user_data = NULL; self->priv->agent_approved_callback = NULL; self->priv->approved_user_data = NULL; self->priv->auto_accept = FALSE; GError *error = NULL; GDBusInterfaceVTable obex_agent_table; memset(&obex_agent_table, 0x0, sizeof(obex_agent_table)); GDBusNodeInfo *obex_agent_node_info = g_dbus_node_info_new_for_xml(_obex_agent_introspect_xml, &error); g_assert(error == NULL); GDBusInterfaceInfo *obex_agent_interface_info = g_dbus_node_info_lookup_interface(obex_agent_node_info, OBEX_AGENT_DBUS_INTERFACE); obex_agent_table.method_call = _obex_agent_method_call_func; self->priv->registration_id = g_dbus_connection_register_object(session_conn, OBEX_AGENT_DBUS_PATH, obex_agent_interface_info, &obex_agent_table, self, _obex_agent_g_destroy_notify, &error); g_assert(error == NULL); g_assert(self->priv->registration_id != 0); g_dbus_node_info_unref(obex_agent_node_info); } static void _obex_agent_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { ObexAgent *self = OBEX_AGENT(object); switch (property_id) { case PROP_ROOT_FOLDER: g_value_set_string(value, self->priv->root_folder); break; case PROP_AUTO_ACCPET: g_value_set_boolean(value, self->priv->auto_accept); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void _obex_agent_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { ObexAgent *self = OBEX_AGENT(object); switch (property_id) { case PROP_ROOT_FOLDER: self->priv->root_folder = g_value_dup_string(value); break; case PROP_AUTO_ACCPET: self->priv->auto_accept = g_value_get_boolean(value); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } /* Constructor */ ObexAgent *obex_agent_new(const gchar *root_folder, const gboolean auto_accept) { return g_object_new(OBEX_AGENT_TYPE, "RootFolder", root_folder, "AutoAccept", auto_accept, NULL); } /* Methods */ static void _obex_agent_method_call_func(GDBusConnection *connection, const gchar *sender, const gchar *object_path, const gchar *interface_name, const gchar *method_name, GVariant *parameters, GDBusMethodInvocation *invocation, gpointer user_data) { g_assert(user_data != NULL); ObexAgent *self = user_data; if (g_strcmp0(method_name, "AuthorizePush") == 0) { const gchar *transfer = g_variant_get_string(g_variant_get_child_value(parameters, 0), NULL); if (intf_supported(OBEX_TRANSFER_DBUS_SERVICE, transfer, OBEX_TRANSFER_DBUS_INTERFACE)) { ObexTransfer *transfer_t = obex_transfer_new(transfer); g_print("[Transfer Request]\n"); g_print(" Name: %s\n", obex_transfer_get_name(transfer_t, NULL)); g_print(" Size: %" G_GINT64_FORMAT " bytes\n", obex_transfer_get_size(transfer_t, NULL)); // Filename seems to be always NULL // g_print(" Filename: %s\n", obex_transfer_get_filename(transfer_t, NULL)); const gchar *filename = obex_transfer_get_name(transfer_t, NULL); const guint64 size = obex_transfer_get_size(transfer_t, NULL); g_object_unref(transfer_t); gchar yn[4] = {0,}; if (TRUE == self->priv->auto_accept) yn[0] = 'y'; else { g_print("Accept (yes/no)? "); errno = 0; if (scanf("%3s", yn) == EOF && errno) { g_warning("%s\n", strerror(errno)); } } if (g_strcmp0(yn, "y") == 0 || g_strcmp0(yn, "yes") == 0) { // IMPORTANT NOTE! // OBEX CANNOT WRITE FILES OUTSIDE OF /home//.cache/obexd // GVariant *ret = g_variant_new("(s)", g_build_filename(self->priv->root_folder, filename, NULL)); // This will store the file in /home//.cache/obexd GVariant *ret = g_variant_new("(s)", filename); // g_print("invocation return value: %s\n", g_variant_print(ret, TRUE)); // Call the callback to handle the filename and size if(self->priv->agent_approved_callback) (*self->priv->agent_approved_callback)(self, transfer, filename, size, self->priv->approved_user_data); // Return string g_dbus_method_invocation_return_value(invocation, ret); return; } else { // Return error g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.obex.Error.Rejected", "File transfer rejected"); return; } } else { g_print("Error: Unknown transfer request\n"); // Return error g_dbus_method_invocation_return_dbus_error(invocation, "org.bluez.obex.Error.Rejected", "File transfer rejected"); return; } } else if (g_strcmp0(method_name, "Cancel") == 0) { g_print("Request cancelled\n"); // Return void g_dbus_method_invocation_return_value(invocation, NULL); return; } else if (g_strcmp0(method_name, "Release") == 0) { if (_update_progress) { g_print("\n"); _update_progress = FALSE; } g_print("OBEXAgent released\n"); (*self->priv->agent_released_callback)(self, self->priv->user_data); // Return void g_dbus_method_invocation_return_value(invocation, NULL); return; } } static void _obex_agent_g_destroy_notify(gpointer data) { g_free(data); } void obex_agent_set_release_callback(ObexAgent *self, ObexAgentReleasedCallback callback_function, gpointer user_data) { g_assert(OBEX_AGENT_IS(self)); self->priv->agent_released_callback = callback_function; self->priv->user_data = user_data; } void obex_agent_clear_release_callback(ObexAgent *self) { g_assert(OBEX_AGENT_IS(self)); self->priv->agent_released_callback = NULL; self->priv->user_data = NULL; } void obex_agent_set_approved_callback(ObexAgent *self, ObexAgentApprovedCallback callback_function, gpointer user_data) { g_assert(OBEX_AGENT_IS(self)); self->priv->agent_approved_callback = callback_function; self->priv->approved_user_data = user_data; } void obex_agent_clear_approved_callback(ObexAgent *self) { g_assert(OBEX_AGENT_IS(self)); self->priv->agent_approved_callback = NULL; self->priv->approved_user_data = NULL; }bluez-tools-2.0~20170911.0.7cb788c/src/lib/obex_agent.h000066400000000000000000000057431315563672100217420ustar00rootroot00000000000000/* * * bluez-tools - a set of tools to manage bluetooth devices for linux * * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __OBEX_AGENT_H #define __OBEX_AGENT_H #ifdef __cplusplus extern "C" { #endif #include #define OBEX_AGENT_DBUS_SERVICE "org.blueztools" #define OBEX_AGENT_DBUS_INTERFACE "org.bluez.obex.Agent1" #define OBEX_AGENT_DBUS_PATH "/org/blueztools/obex" /* * Type macros */ #define OBEX_AGENT_TYPE (obex_agent_get_type()) #define OBEX_AGENT(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), OBEX_AGENT_TYPE, ObexAgent)) #define OBEX_AGENT_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE((obj), OBEX_AGENT_TYPE)) #define OBEX_AGENT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST((klass), OBEX_AGENT_TYPE, ObexAgentClass)) #define OBEX_AGENT_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE((klass), OBEX_AGENT_TYPE)) #define OBEX_AGENT_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS((obj), OBEX_AGENT_TYPE, ObexAgentClass)) typedef struct _ObexAgent ObexAgent; typedef struct _ObexAgentClass ObexAgentClass; typedef struct _ObexAgentPrivate ObexAgentPrivate; struct _ObexAgent { GObject parent_instance; /*< private >*/ ObexAgentPrivate *priv; }; struct _ObexAgentClass { GObjectClass parent_class; }; /* used by OBEX_AGENT_TYPE */ GType obex_agent_get_type(void) G_GNUC_CONST; // agent released callback pointer function typedef void (*ObexAgentReleasedCallback)(ObexAgent *obex_agent, gpointer user_data); // agent approved callback pointer function typedef void (*ObexAgentApprovedCallback)(ObexAgent *obex_agent, const gchar* obex_transfer_path, const gchar *name, const guint64 size, gpointer user_data); /* * Constructor */ ObexAgent *obex_agent_new(const gchar *root_folder, const gboolean auto_accept); /* * Method definitions */ void obex_agent_progress(ObexAgent *self, const gchar *transfer, guint64 transferred, GError **error); void obex_agent_set_release_callback(ObexAgent *self, ObexAgentReleasedCallback callback_function, gpointer user_data); void obex_agent_clear_release_callback(ObexAgent *self); void obex_agent_set_approved_callback(ObexAgent *self, ObexAgentApprovedCallback callback_function, gpointer user_data); void obex_agent_clear_approved_callback(ObexAgent *self); #ifdef __cplusplus } #endif #endif /* __OBEX_AGENT_H */ bluez-tools-2.0~20170911.0.7cb788c/src/lib/properties.c000066400000000000000000000217441315563672100220150ustar00rootroot00000000000000#include #include "dbus-common.h" #include "properties.h" struct _PropertiesPrivate { GDBusProxy *proxy; // a{sa{sv}} GVariant *dict_interfaces; gchar *dbus_type; gchar *dbus_service_name; gchar *dbus_object_path; }; G_DEFINE_TYPE_WITH_PRIVATE (Properties, properties, G_TYPE_OBJECT) enum { PROP_0, PROP_DBUS_TYPE, PROP_DBUS_SERVICE_NAME, PROP_DBUS_OBJECT_PATH, N_PROPERTIES }; /* Keep a pointer to the properties definition */ static GParamSpec *obj_properties[N_PROPERTIES] = { NULL, }; /* * Private method definitions */ static void _properties_create_gdbus_proxy(Properties *self, GError **error); /* * Methods */ static void _properties_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { Properties *self = PROPERTIES(object); GError *error = NULL; switch (property_id) { // case PROP_EXAMPLE: // g_free(self->priv->example); // self->priv->example = g_value_dup_string(value); // g_print("example: %s\n", self->priv->example); // break; case PROP_DBUS_TYPE: if(self->priv->dbus_type) g_free(self->priv->dbus_type); self->priv->dbus_type = g_value_dup_string(value); // _properties_set_dbus_object_path(self, g_value_dup_string(value), &error); _properties_create_gdbus_proxy(self, &error); break; case PROP_DBUS_SERVICE_NAME: if(self->priv->dbus_service_name) g_free(self->priv->dbus_service_name); self->priv->dbus_service_name = g_value_dup_string(value); // _properties_set_dbus_object_path(self, g_value_dup_string(value), &error); _properties_create_gdbus_proxy(self, &error); break; case PROP_DBUS_OBJECT_PATH: if(self->priv->dbus_object_path) g_free(self->priv->dbus_object_path); self->priv->dbus_object_path = g_value_dup_string(value); // _properties_set_dbus_object_path(self, g_value_dup_string(value), &error); _properties_create_gdbus_proxy(self, &error); break; default: /* We don't have any other property... */ G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } g_assert(error == NULL); } static void _properties_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { Properties *self = PROPERTIES(object); switch (property_id) { // case PROP_EXAMPLE: // g_value_set_string(value, self->priv->example); // break; case PROP_DBUS_TYPE: g_value_set_string(value, properties_get_dbus_type(self)); break; case PROP_DBUS_SERVICE_NAME: g_value_set_string(value, properties_get_dbus_service_name(self)); break; case PROP_DBUS_OBJECT_PATH: g_value_set_string(value, properties_get_dbus_object_path(self)); break; default: /* We don't have any other property... */ G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void properties_dispose (GObject *gobject) { Properties *self = PROPERTIES (gobject); /* In dispose(), you are supposed to free all types referenced from this * object which might themselves hold a reference to self. Generally, * the most simple solution is to unref all members on which you own a * reference. */ /* dispose() might be called multiple times, so we must guard against * calling g_object_unref() on an invalid GObject by setting the member * NULL; g_clear_object() does this for us, atomically. */ // g_clear_object (&self->priv->an_object); g_clear_object (&self->priv->proxy); if(self->priv->dict_interfaces != NULL) g_variant_unref(self->priv->dict_interfaces); /* Always chain up to the parent class; there is no need to check if * the parent class implements the dispose() virtual function: it is * always guaranteed to do so */ G_OBJECT_CLASS (properties_parent_class)->dispose (gobject); } static void properties_finalize (GObject *gobject) { Properties *self = PROPERTIES(gobject); // g_free(self->priv->a_string); /* Always chain up to the parent class; as with dispose(), finalize() * is guaranteed to exist on the parent's class virtual function table */ G_OBJECT_CLASS (properties_parent_class)->finalize (gobject); } static void properties_class_init (PropertiesClass *klass) { GObjectClass *gobject_class = G_OBJECT_CLASS (klass); gobject_class->get_property = _properties_get_property; gobject_class->set_property = _properties_set_property; /* object DBusType [readwrite, construct only] */ obj_properties[PROP_DBUS_TYPE] = g_param_spec_string ("DBusType", "dbus_type", "Properties D-Bus connection type", NULL /* default value */, G_PARAM_CONSTRUCT_ONLY | G_PARAM_READWRITE); /* object DBusServiceName [readwrite, construct only] */ obj_properties[PROP_DBUS_SERVICE_NAME] = g_param_spec_string ("DBusServiceName", "dbus_service_name", "Properties D-Bus service name", NULL /* default value */, G_PARAM_CONSTRUCT_ONLY | G_PARAM_READWRITE); /* object DBusObjectPath [readwrite, construct only] */ obj_properties[PROP_DBUS_OBJECT_PATH] = g_param_spec_string ("DBusObjectPath", "dbus_object_path", "Properties D-Bus object path", NULL /* default value */, G_PARAM_CONSTRUCT_ONLY | G_PARAM_READWRITE); g_object_class_install_properties (gobject_class, N_PROPERTIES, obj_properties); } static void properties_init (Properties *self) { self->priv = properties_get_instance_private (self); self->priv->proxy = NULL; self->priv->dict_interfaces = NULL; self->priv->dbus_type = NULL; self->priv->dbus_service_name = NULL; self->priv->dbus_object_path = NULL; } static void _properties_create_gdbus_proxy(Properties *self, GError **error) { if(self->priv->dbus_type && self->priv->dbus_service_name && self->priv->dbus_object_path) { if(g_ascii_strcasecmp(g_ascii_strdown(self->priv->dbus_type, -1), "system") == 0) { g_assert(system_conn != NULL); self->priv->proxy = g_dbus_proxy_new_sync(system_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, self->priv->dbus_service_name, self->priv->dbus_object_path, PROPERTIES_DBUS_INTERFACE, NULL, error); } else if(g_ascii_strcasecmp(g_ascii_strdown(self->priv->dbus_type, -1), "session") == 0) { g_assert(session_conn != NULL); self->priv->proxy = g_dbus_proxy_new_sync(session_conn, G_DBUS_PROXY_FLAGS_NONE, NULL, self->priv->dbus_service_name, self->priv->dbus_object_path, PROPERTIES_DBUS_INTERFACE, NULL, error); } else g_error("Invalid DBus connection type: %s", self->priv->dbus_type); } } const gchar *properties_get_dbus_type(Properties *self) { g_assert(PROPERTIES_IS(self)); g_assert(self->priv->proxy != NULL); return self->priv->dbus_type; } const gchar *properties_get_dbus_service_name(Properties *self) { g_assert(PROPERTIES_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_name(self->priv->proxy); } const gchar *properties_get_dbus_object_path(Properties *self) { g_assert(PROPERTIES_IS(self)); g_assert(self->priv->proxy != NULL); return g_dbus_proxy_get_object_path(self->priv->proxy); } GVariant *properties_get(Properties *self, const gchar *interface_name, const gchar *property_name, GError **error) { g_assert(PROPERTIES_IS(self)); GVariant *retVal = g_dbus_proxy_call_sync(self->priv->proxy, "Get", g_variant_new("(ss)", interface_name, property_name), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (retVal == NULL) return NULL; retVal = g_variant_get_child_value(retVal, 0); retVal = g_variant_get_variant(retVal); return retVal; } void properties_set(Properties *self, const gchar *interface_name, const gchar *property_name, const GVariant *value, GError **error) { g_assert(PROPERTIES_IS(self)); g_dbus_proxy_call_sync(self->priv->proxy, "Set", g_variant_new("(ssv)", interface_name, property_name, value), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); } GVariant *properties_get_all(Properties *self, const gchar *interface_name, GError **error) { g_assert(PROPERTIES_IS(self)); GVariant *retVal = g_dbus_proxy_call_sync(self->priv->proxy, "GetAll", g_variant_new("(s)", interface_name), G_DBUS_CALL_FLAGS_NONE, -1, NULL, error); if (retVal == NULL) return NULL; retVal = g_variant_get_child_value(retVal, 0); return retVal; }bluez-tools-2.0~20170911.0.7cb788c/src/lib/properties.h000066400000000000000000000036421315563672100220170ustar00rootroot00000000000000#ifndef PROPERTIES_H #define PROPERTIES_H #ifdef __cplusplus extern "C" { #endif #include /* * Potentially, include other headers on which this header depends. */ /* * Type macros. */ #define PROPERTIES_TYPE (properties_get_type ()) #define PROPERTIES(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), PROPERTIES_TYPE, Properties)) #define PROPERTIES_IS(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), PROPERTIES_TYPE)) #define PROPERTIES_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), PROPERTIES_TYPE, PropertiesClass)) #define PROPERTIES_IS_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), PROPERTIES_TYPE)) #define PROPERTIES_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), PROPERTIES_TYPE, PropertiesClass)) #define PROPERTIES_DBUS_INTERFACE "org.freedesktop.DBus.Properties" typedef struct _Properties Properties; typedef struct _PropertiesPrivate PropertiesPrivate; typedef struct _PropertiesClass PropertiesClass; struct _Properties { /* Parent instance structure */ GObject parent_instance; /* instance members */ PropertiesPrivate *priv; }; struct _PropertiesClass { /* Parent class structure */ GObjectClass parent_class; /* class members */ }; /* used by PROPERTIES_TYPE */ GType properties_get_type(void); /* * Method definitions. */ const gchar *properties_get_dbus_type(Properties *self); const gchar *properties_get_dbus_service_name(Properties *self); const gchar *properties_get_dbus_object_path(Properties *self); GVariant *properties_get(Properties *self, const gchar *interface_name, const gchar *property_name, GError **error); void properties_set(Properties *self, const gchar *interface_name, const gchar *property_name, const GVariant *value, GError **error); GVariant *properties_get_all(Properties *self, const gchar *interface_name, GError **error); #ifdef __cplusplus } #endif #endif /* PROPERTIES_H */bluez-tools-2.0~20170911.0.7cb788c/src/lib/sdp.c000066400000000000000000000231621315563672100204030ustar00rootroot00000000000000/* * * BlueZ - Bluetooth protocol stack for Linux * * Copyright (C) 2001-2002 Ricky Yuen * Copyright (C) 2003-2007 Marcel Holtmann * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include #include "sdp.h" /* UUID name lookup table */ typedef struct { int uuid; char* name; } sdp_uuid_nam_lookup_table_t; static sdp_uuid_nam_lookup_table_t sdp_uuid_nam_lookup_table[] = { { SDP_UUID_SDP, "SDP" }, { SDP_UUID_UDP, "UDP" }, { SDP_UUID_RFCOMM, "RFCOMM" }, { SDP_UUID_TCP, "TCP" }, { SDP_UUID_TCS_BIN, "TCS-BIN" }, { SDP_UUID_TCS_AT, "TCS-AT" }, { SDP_UUID_OBEX, "OBEX" }, { SDP_UUID_IP, "IP" }, { SDP_UUID_FTP, "FTP" }, { SDP_UUID_HTTP, "HTTP" }, { SDP_UUID_WSP, "WSP" }, { SDP_UUID_L2CAP, "L2CAP" }, { SDP_UUID_BNEP, "BNEP" }, /* PAN */ { SDP_UUID_HIDP, "HIDP" }, /* HID */ { SDP_UUID_AVCTP, "AVCTP" }, /* AVCTP */ { SDP_UUID_AVDTP, "AVDTP" }, /* AVDTP */ { SDP_UUID_CMTP, "CMTP" }, /* CIP */ { SDP_UUID_UDI_C_PLANE, "UDI_C-Plane" }, /* UDI */ { SDP_UUID_SERVICE_DISCOVERY_SERVER, "SDServer" }, { SDP_UUID_BROWSE_GROUP_DESCRIPTOR, "BrwsGrpDesc" }, { SDP_UUID_PUBLIC_BROWSE_GROUP, "PubBrwsGrp" }, { SDP_UUID_SERIAL_PORT, "SP" }, { SDP_UUID_LAN_ACCESS_PPP, "LAN" }, { SDP_UUID_DIALUP_NETWORKING, "DUN" }, { SDP_UUID_IR_MC_SYNC, "IRMCSync" }, { SDP_UUID_OBEX_OBJECT_PUSH, "OBEXObjPush" }, { SDP_UUID_OBEX_FILE_TRANSFER, "OBEXObjTrnsf" }, { SDP_UUID_IR_MC_SYNC_COMMAND, "IRMCSyncCmd" }, { SDP_UUID_HEADSET, "Headset" }, { SDP_UUID_CORDLESS_TELEPHONY, "CordlessTel" }, { SDP_UUID_AUDIO_SOURCE, "AudioSource" }, /* A2DP */ { SDP_UUID_AUDIO_SINK, "AudioSink" }, /* A2DP */ { SDP_UUID_AV_REMOTE_TARGET, "AVRemTarget" }, /* AVRCP */ { SDP_UUID_ADVANCED_AUDIO, "AdvAudio" }, /* A2DP */ { SDP_UUID_AV_REMOTE, "AVRemote" }, /* AVRCP */ { SDP_UUID_VIDEO_CONFERENCING, "VideoConf" }, /* VCP */ { SDP_UUID_INTERCOM, "Intercom" }, { SDP_UUID_FAX, "Fax" }, { SDP_UUID_HEADSET_AUDIO_GATEWAY, "Headset AG" }, { SDP_UUID_WAP, "WAP" }, { SDP_UUID_WAP_CLIENT, "WAP Client" }, { SDP_UUID_PANU, "PANU" }, /* PAN */ { SDP_UUID_NAP, "NAP" }, /* PAN */ { SDP_UUID_GN, "GN" }, /* PAN */ { SDP_UUID_DIRECT_PRINTING, "DirectPrint" }, /* BPP */ { SDP_UUID_REFERENCE_PRINTING, "RefPrint" }, /* BPP */ { SDP_UUID_IMAGING, "Imaging" }, /* BIP */ { SDP_UUID_IMAGING_RESPONDER, "ImagingResp" }, /* BIP */ { SDP_UUID_HANDSFREE, "Handsfree" }, { SDP_UUID_HANDSFREE_AUDIO_GATEWAY, "Handsfree AG" }, { SDP_UUID_DIRECT_PRINTING_REF_OBJS, "RefObjsPrint" }, /* BPP */ { SDP_UUID_REFLECTED_UI, "ReflectedUI" }, /* BPP */ { SDP_UUID_BASIC_PRINTING, "BasicPrint" }, /* BPP */ { SDP_UUID_PRINTING_STATUS, "PrintStatus" }, /* BPP */ { SDP_UUID_HUMAN_INTERFACE_DEVICE, "HID" }, /* HID */ { SDP_UUID_HARDCOPY_CABLE_REPLACE, "HCRP" }, /* HCRP */ { SDP_UUID_HCR_PRINT, "HCRPrint" }, /* HCRP */ { SDP_UUID_HCR_SCAN, "HCRScan" }, /* HCRP */ { SDP_UUID_COMMON_ISDN_ACCESS, "CIP" }, /* CIP */ { SDP_UUID_VIDEO_CONFERENCING_GW, "VideoConf GW" }, /* VCP */ { SDP_UUID_UDI_MT, "UDI MT" }, /* UDI */ { SDP_UUID_UDI_TA, "UDI TA" }, /* UDI */ { SDP_UUID_AUDIO_VIDEO, "AudioVideo" }, /* VCP */ { SDP_UUID_SIM_ACCESS, "SAP" }, /* SAP */ { SDP_UUID_PHONEBOOK_ACCESS_PCE, "PBAP PCE" }, /* PBAP */ { SDP_UUID_PHONEBOOK_ACCESS_PSE, "PBAP PSE" }, /* PBAP */ { SDP_UUID_PHONEBOOK_ACCESS, "PBAP" }, /* PBAP */ { SDP_UUID_PNP_INFORMATION, "PNPInfo" }, { SDP_UUID_GENERIC_NETWORKING, "Networking" }, { SDP_UUID_GENERIC_FILE_TRANSFER, "FileTrnsf" }, { SDP_UUID_GENERIC_AUDIO, "Audio" }, { SDP_UUID_GENERIC_TELEPHONY, "Telephony" }, { SDP_UUID_UPNP_SERVICE, "UPNP" }, /* ESDP */ { SDP_UUID_UPNP_IP_SERVICE, "UPNP IP" }, /* ESDP */ { SDP_UUID_ESDP_UPNP_IP_PAN, "UPNP PAN" }, /* ESDP */ { SDP_UUID_ESDP_UPNP_IP_LAP, "UPNP LAP" }, /* ESDP */ { SDP_UUID_ESDP_UPNP_L2CAP, "UPNP L2CAP" }, /* ESDP */ { SDP_UUID_VIDEO_SOURCE, "VideoSource" }, /* VDP */ { SDP_UUID_VIDEO_SINK, "VideoSink" }, /* VDP */ { SDP_UUID_VIDEO_DISTRIBUTION, "VideoDist" }, /* VDP */ { SDP_UUID_APPLE_AGENT, "AppleAgent" }, }; #define SDP_UUID_NAM_LOOKUP_TABLE_SIZE \ (sizeof(sdp_uuid_nam_lookup_table)/sizeof(sdp_uuid_nam_lookup_table_t)) /* AttrID name lookup table */ typedef struct { int attr_id; char* name; } sdp_attr_id_nam_lookup_table_t; static sdp_attr_id_nam_lookup_table_t sdp_attr_id_nam_lookup_table[] = { { SDP_ATTR_ID_SERVICE_RECORD_HANDLE, "SrvRecHndl" }, { SDP_ATTR_ID_SERVICE_CLASS_ID_LIST, "SrvClassIDList" }, { SDP_ATTR_ID_SERVICE_RECORD_STATE, "SrvRecState" }, { SDP_ATTR_ID_SERVICE_SERVICE_ID, "SrvID" }, { SDP_ATTR_ID_PROTOCOL_DESCRIPTOR_LIST, "ProtocolDescList" }, { SDP_ATTR_ID_BROWSE_GROUP_LIST, "BrwGrpList" }, { SDP_ATTR_ID_LANGUAGE_BASE_ATTRIBUTE_ID_LIST, "LangBaseAttrIDList" }, { SDP_ATTR_ID_SERVICE_INFO_TIME_TO_LIVE, "SrvInfoTimeToLive" }, { SDP_ATTR_ID_SERVICE_AVAILABILITY, "SrvAvail" }, { SDP_ATTR_ID_BLUETOOTH_PROFILE_DESCRIPTOR_LIST, "BTProfileDescList" }, { SDP_ATTR_ID_DOCUMENTATION_URL, "DocURL" }, { SDP_ATTR_ID_CLIENT_EXECUTABLE_URL, "ClientExeURL" }, { SDP_ATTR_ID_ICON_10, "Icon10" }, { SDP_ATTR_ID_ICON_URL, "IconURL" }, { SDP_ATTR_ID_SERVICE_NAME, "SrvName" }, { SDP_ATTR_ID_SERVICE_DESCRIPTION, "SrvDesc" }, { SDP_ATTR_ID_PROVIDER_NAME, "ProviderName" }, { SDP_ATTR_ID_VERSION_NUMBER_LIST, "VersionNumList" }, { SDP_ATTR_ID_GROUP_ID, "GrpID" }, { SDP_ATTR_ID_SERVICE_DATABASE_STATE, "SrvDBState" }, { SDP_ATTR_ID_SERVICE_VERSION, "SrvVersion" }, { SDP_ATTR_ID_SECURITY_DESCRIPTION, "SecurityDescription"}, /* PAN */ { SDP_ATTR_ID_SUPPORTED_DATA_STORES_LIST, "SuppDataStoresList" }, /* Synchronization */ { SDP_ATTR_ID_SUPPORTED_FORMATS_LIST, "SuppFormatsList" }, /* OBEX Object Push */ { SDP_ATTR_ID_NET_ACCESS_TYPE, "NetAccessType" }, /* PAN */ { SDP_ATTR_ID_MAX_NET_ACCESS_RATE, "MaxNetAccessRate" }, /* PAN */ { SDP_ATTR_ID_IPV4_SUBNET, "IPv4Subnet" }, /* PAN */ { SDP_ATTR_ID_IPV6_SUBNET, "IPv6Subnet" }, /* PAN */ { SDP_ATTR_ID_SUPPORTED_CAPABILITIES, "SuppCapabilities" }, /* Imaging */ { SDP_ATTR_ID_SUPPORTED_FEATURES, "SuppFeatures" }, /* Imaging and Hansfree */ { SDP_ATTR_ID_SUPPORTED_FUNCTIONS, "SuppFunctions" }, /* Imaging */ { SDP_ATTR_ID_TOTAL_IMAGING_DATA_CAPACITY, "SuppTotalCapacity" }, /* Imaging */ { SDP_ATTR_ID_SUPPORTED_REPOSITORIES, "SuppRepositories" }, /* PBAP */ }; #define SDP_ATTR_ID_NAM_LOOKUP_TABLE_SIZE \ (sizeof(sdp_attr_id_nam_lookup_table)/sizeof(sdp_attr_id_nam_lookup_table_t)) const char* sdp_get_uuid_name(int uuid) { for (int i = 0; i < SDP_UUID_NAM_LOOKUP_TABLE_SIZE; i++) { if (sdp_uuid_nam_lookup_table[i].uuid == uuid) return sdp_uuid_nam_lookup_table[i].name; } return NULL; } const char* sdp_get_attr_id_name(int attr_id) { for (int i = 0; i < SDP_ATTR_ID_NAM_LOOKUP_TABLE_SIZE; i++) if (sdp_attr_id_nam_lookup_table[i].attr_id == attr_id) return sdp_attr_id_nam_lookup_table[i].name; return NULL; } bluez-tools-2.0~20170911.0.7cb788c/src/lib/sdp.h000066400000000000000000000231621315563672100204100ustar00rootroot00000000000000/* * * BlueZ - Bluetooth protocol stack for Linux * * Copyright (C) 2001-2002 Ricky Yuen * Copyright (C) 2003-2007 Marcel Holtmann * Copyright (C) 2010 Alexander Orlenko * * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA * */ #ifndef __SDP_H #define __SDP_H /* Bluetooth assigned UUIDs for protocols */ #define SDP_UUID_SDP 0x0001 #define SDP_UUID_UDP 0x0002 #define SDP_UUID_RFCOMM 0x0003 #define SDP_UUID_TCP 0x0004 #define SDP_UUID_TCS_BIN 0x0005 #define SDP_UUID_TCS_AT 0x0006 #define SDP_UUID_OBEX 0x0008 #define SDP_UUID_IP 0x0009 #define SDP_UUID_FTP 0x000A #define SDP_UUID_HTTP 0x000C #define SDP_UUID_WSP 0x000E #define SDP_UUID_BNEP 0x000F /* PAN */ #define SDP_UUID_HIDP 0x0011 /* HID */ #define SDP_UUID_HARDCOPY_CONTROL_CHANNEL 0x0012 /* HCRP */ #define SDP_UUID_HARDCOPY_DATA_CHANNEL 0x0014 /* HCRP */ #define SDP_UUID_HARDCOPY_NOTIFICATION 0x0016 /* HCRP */ #define SDP_UUID_AVCTP 0x0017 /* AVCTP */ #define SDP_UUID_AVDTP 0x0019 /* AVDTP */ #define SDP_UUID_CMTP 0x001B /* CIP */ #define SDP_UUID_UDI_C_PLANE 0x001D /* UDI */ #define SDP_UUID_L2CAP 0x0100 /* Bluetooth assigned UUIDs for Service Classes */ #define SDP_UUID_SERVICE_DISCOVERY_SERVER 0x1000 #define SDP_UUID_BROWSE_GROUP_DESCRIPTOR 0x1001 #define SDP_UUID_PUBLIC_BROWSE_GROUP 0x1002 #define SDP_UUID_SERIAL_PORT 0x1101 #define SDP_UUID_LAN_ACCESS_PPP 0x1102 #define SDP_UUID_DIALUP_NETWORKING 0x1103 #define SDP_UUID_IR_MC_SYNC 0x1104 #define SDP_UUID_OBEX_OBJECT_PUSH 0x1105 #define SDP_UUID_OBEX_FILE_TRANSFER 0x1106 #define SDP_UUID_IR_MC_SYNC_COMMAND 0x1107 #define SDP_UUID_HEADSET 0x1108 #define SDP_UUID_CORDLESS_TELEPHONY 0x1109 #define SDP_UUID_AUDIO_SOURCE 0x110a /* A2DP */ #define SDP_UUID_AUDIO_SINK 0x110b /* A2DP */ #define SDP_UUID_AV_REMOTE_TARGET 0x110c /* AVRCP */ #define SDP_UUID_ADVANCED_AUDIO 0x110d /* A2DP */ #define SDP_UUID_AV_REMOTE 0x110e /* AVRCP */ #define SDP_UUID_VIDEO_CONFERENCING 0x110f /* VCP */ #define SDP_UUID_INTERCOM 0x1110 #define SDP_UUID_FAX 0x1111 #define SDP_UUID_HEADSET_AUDIO_GATEWAY 0x1112 #define SDP_UUID_WAP 0x1113 #define SDP_UUID_WAP_CLIENT 0x1114 #define SDP_UUID_PANU 0x1115 /* PAN */ #define SDP_UUID_NAP 0x1116 /* PAN */ #define SDP_UUID_GN 0x1117 /* PAN */ #define SDP_UUID_DIRECT_PRINTING 0x1118 /* BPP */ #define SDP_UUID_REFERENCE_PRINTING 0x1119 /* BPP */ #define SDP_UUID_IMAGING 0x111a /* BIP */ #define SDP_UUID_IMAGING_RESPONDER 0x111b /* BIP */ #define SDP_UUID_IMAGING_AUTOMATIC_ARCHIVE 0x111c /* BIP */ #define SDP_UUID_IMAGING_REFERENCED_OBJECTS 0x111d /* BIP */ #define SDP_UUID_HANDSFREE 0x111e #define SDP_UUID_HANDSFREE_AUDIO_GATEWAY 0x111f #define SDP_UUID_DIRECT_PRINTING_REF_OBJS 0x1120 /* BPP */ #define SDP_UUID_DIRECT_PRINTING_REFERENCE_OBJECTS 0x1120 /* BPP */ #define SDP_UUID_REFLECTED_UI 0x1121 /* BPP */ #define SDP_UUID_BASIC_PRINTING 0x1122 /* BPP */ #define SDP_UUID_PRINTING_STATUS 0x1123 /* BPP */ #define SDP_UUID_HUMAN_INTERFACE_DEVICE 0x1124 /* HID */ #define SDP_UUID_HARDCOPY_CABLE_REPLACE 0x1125 /* HCRP */ #define SDP_UUID_HCR_PRINT 0x1126 /* HCRP */ #define SDP_UUID_HCR_SCAN 0x1127 /* HCRP */ #define SDP_UUID_COMMON_ISDN_ACCESS 0x1128 /* CIP */ #define SDP_UUID_VIDEO_CONFERENCING_GW 0x1129 /* VCP */ #define SDP_UUID_UDI_MT 0x112a /* UDI */ #define SDP_UUID_UDI_TA 0x112b /* UDI */ #define SDP_UUID_AUDIO_VIDEO 0x112c /* VCP */ #define SDP_UUID_SIM_ACCESS 0x112d /* SAP */ #define SDP_UUID_PHONEBOOK_ACCESS_PCE 0x112e /* PBAP */ #define SDP_UUID_PHONEBOOK_ACCESS_PSE 0x112f /* PBAP */ #define SDP_UUID_PHONEBOOK_ACCESS 0x1130 /* PBAP */ #define SDP_UUID_PNP_INFORMATION 0x1200 #define SDP_UUID_GENERIC_NETWORKING 0x1201 #define SDP_UUID_GENERIC_FILE_TRANSFER 0x1202 #define SDP_UUID_GENERIC_AUDIO 0x1203 #define SDP_UUID_GENERIC_TELEPHONY 0x1204 #define SDP_UUID_UPNP_SERVICE 0x1205 /* ESDP */ #define SDP_UUID_UPNP_IP_SERVICE 0x1206 /* ESDP */ #define SDP_UUID_ESDP_UPNP_IP_PAN 0x1300 /* ESDP */ #define SDP_UUID_ESDP_UPNP_IP_LAP 0x1301 /* ESDP */ #define SDP_UUID_ESDP_UPNP_L2CAP 0x1302 /* ESDP */ #define SDP_UUID_VIDEO_SOURCE 0x1303 /* VDP */ #define SDP_UUID_VIDEO_SINK 0x1304 /* VDP */ #define SDP_UUID_VIDEO_DISTRIBUTION 0x1305 /* VDP */ #define SDP_UUID_APPLE_AGENT 0x2112 /* Bluetooth assigned numbers for Attribute IDs */ #define SDP_ATTR_ID_SERVICE_RECORD_HANDLE 0x0000 #define SDP_ATTR_ID_SERVICE_CLASS_ID_LIST 0x0001 #define SDP_ATTR_ID_SERVICE_RECORD_STATE 0x0002 #define SDP_ATTR_ID_SERVICE_SERVICE_ID 0x0003 #define SDP_ATTR_ID_PROTOCOL_DESCRIPTOR_LIST 0x0004 #define SDP_ATTR_ID_BROWSE_GROUP_LIST 0x0005 #define SDP_ATTR_ID_LANGUAGE_BASE_ATTRIBUTE_ID_LIST 0x0006 #define SDP_ATTR_ID_SERVICE_INFO_TIME_TO_LIVE 0x0007 #define SDP_ATTR_ID_SERVICE_AVAILABILITY 0x0008 #define SDP_ATTR_ID_BLUETOOTH_PROFILE_DESCRIPTOR_LIST 0x0009 #define SDP_ATTR_ID_DOCUMENTATION_URL 0x000A #define SDP_ATTR_ID_CLIENT_EXECUTABLE_URL 0x000B #define SDP_ATTR_ID_ICON_10 0x000C #define SDP_ATTR_ID_ICON_URL 0x000D #define SDP_ATTR_ID_SERVICE_NAME 0x0100 #define SDP_ATTR_ID_SERVICE_DESCRIPTION 0x0101 #define SDP_ATTR_ID_PROVIDER_NAME 0x0102 #define SDP_ATTR_ID_VERSION_NUMBER_LIST 0x0200 #define SDP_ATTR_ID_GROUP_ID 0x0200 #define SDP_ATTR_ID_SERVICE_DATABASE_STATE 0x0201 #define SDP_ATTR_ID_SERVICE_VERSION 0x0300 #define SDP_ATTR_ID_EXTERNAL_NETWORK 0x0301 /* Cordless Telephony */ #define SDP_ATTR_ID_SUPPORTED_DATA_STORES_LIST 0x0301 /* Synchronization */ #define SDP_ATTR_ID_REMOTE_AUDIO_VOLUME_CONTROL 0x0302 /* GAP */ #define SDP_ATTR_ID_SUPPORTED_FORMATS_LIST 0x0303 /* OBEX Object Push */ #define SDP_ATTR_ID_FAX_CLASS_1_SUPPORT 0x0302 /* Fax */ #define SDP_ATTR_ID_FAX_CLASS_2_0_SUPPORT 0x0303 #define SDP_ATTR_ID_FAX_CLASS_2_SUPPORT 0x0304 #define SDP_ATTR_ID_AUDIO_FEEDBACK_SUPPORT 0x0305 #define SDP_ATTR_ID_SECURITY_DESCRIPTION 0x030a /* PAN */ #define SDP_ATTR_ID_NET_ACCESS_TYPE 0x030b /* PAN */ #define SDP_ATTR_ID_MAX_NET_ACCESS_RATE 0x030c /* PAN */ #define SDP_ATTR_ID_IPV4_SUBNET 0x030d /* PAN */ #define SDP_ATTR_ID_IPV6_SUBNET 0x030e /* PAN */ #define SDP_ATTR_ID_SUPPORTED_CAPABILITIES 0x0310 /* Imaging */ #define SDP_ATTR_ID_SUPPORTED_FEATURES 0x0311 /* Imaging and Hansfree */ #define SDP_ATTR_ID_SUPPORTED_FUNCTIONS 0x0312 /* Imaging */ #define SDP_ATTR_ID_TOTAL_IMAGING_DATA_CAPACITY 0x0313 /* Imaging */ #define SDP_ATTR_ID_SUPPORTED_REPOSITORIES 0x0314 /* PBAP */ const char* sdp_get_uuid_name(int uuid); const char* sdp_get_attr_id_name(int attr_id); #endif /* __SDP_H */