KeyHoleTV開発者のブログ

日々の質問や開発の日記

CSS HTML iOS Safari に悩む

KeyHoleTVのホームページ OISEYER Inc. は、ダサイデザインで、開発者が手で書いている。 HTMLやCSSを emacs で記述しており、デザインツールのたぐいは、gimp と OpneOffice ぐらいである。 デバックは、appach をCentOSにいれて、それで、動作の検証をしている。

 

ホームページの中で、チェックボックスにチエックを入れると、ボタンが有効になる部分がある。今まででは、JavaScript を使っていたが、CSSでも出来そうなので、CSSに書き換えた。

処理は、

HTMLとCSSだけ!要素の表示・非表示を切り替える方法

[CSS]チェックボックスにチェックを入れた時に要素に変化を付ける方法|CSS擬似要素・擬似クラス|WEBデザインの小ネタとTIPSのまとめサイト「ウェブアンテナ」

を参考にした。 

これらのページで紹介されているCSSで肝になる部分は、おそらく、

.hidden_box .hidden_show {
    height: 0;
}
.hidden_box input:checked ~ .hidden_show { height: auto; }

div.changed {
    color: #000;
}
input[type=checkbox]:checked ~ div.changed {
    color: #ff0000;
}
であろうと思う。 これらは、 inputタグで、タイプがcheckbox の時、checkedされているか、いないかで、対象の属性を変える。 上記の例では、checkedされているとき、 .hidden_show、.div.changedの属性を更新するようになっている。 個人的に思う重要な点は、属性の更新ができるものとできないものがあるという点。 例えば、buttonには、 disabledという属性があるが、CSSでは、どうもこの属性の更新ができないようだ。 例えば、 disabled:none; ができると、便利だと思うのだが。 (display:none; は、できるくせに、何故だ。Javascriptを押す人たちが強く主張しているからなのか) これをするためには、JavaScript を用いるしか方法がないみたい。 方法があったら、教えてほしい。
 
HTMLでは、
<label for="label2">クリックして表示</label>
<input type="checkbox" id="label2"/>
<input type="checkbox" id="toggle">
<label for="toggle">Toggle Button</label>
となっている。 
 
さて、iOSのSafariである。 iOSのSafari は、ボタンのtypeやinput のタイプにsubmitを指定すると( <button type="submit" ...> <input type="submit"..> )、
表示上では、頑なに、トラックの絵のボタンになってしまう。 だから、
<button type="submit" ...>
<img src="xxx" ...>
テキスト
</button>
で括った場合でも、img やテキストが表示されず、細長いトラックの絵になってしまう。 同じSafariでもMacでは、img やテキストが表示される。
これを解消するために、google でいろいろ探したら、
input[type='submit']
{
   -webkit-appearance: none;
}
に行き着く。 どうやら、' -webkit-appearance:'
の属性をnoneにしないといけないようだ。 でもこれでは、正しく表示されない。 理由は、input タグを用いていること。  input タグのタイプがsubmitの場合、 -webkit-appearance をnoneにしている。 上記のbutton の場合、
button [type="submit"]
{
    -webkit-appearance: none;
}
としないといけない。 これで、iOSのSafariでも正しく表示された。 この書き方は、いろいろ探したが、でてこない。 CSSやHTMLを扱っている人にとっては、当然なのかもしれないが、答えを見つけるまで、えらく苦労した。  まず、button に [type="submit"] が使えるかどうか分からないし、タグは、なんでもよいのかもよく分からない。 個人的には、[type="submit"] は、いろいろなサイトで紹介されており、上の例でもあるように input タグの専売のように見えてしまう。
 
サイトで、<button ..> タグにする必要性は、 販売用のJavaScript がどうやら、 buttonタグ のtype しかみておらず、input タグのtype="submit" にしても、JavaScript がそれに反応しない。 当然
idや名前もbutton のものと同じにしても、JavaScript が反応しない。 これも理由がよく分からない。
<form> で囲っているので、 その中にある input であろうが、buttonであろうが、 変わらないような気がしてならないのだが。。。
 
なお、KeyHoleTVのダウンロード・プレミアムモジュールキーの販売は、

www.oiseyer.com

 で。
 
 
 
 

 

iOS 12 は、おそらく不具合がある

原因の発覚

iOS12 にアップグレードしたら、i-KeyHoleTVが動作しなくなったと利用者から報告があった。手持ちのiPhoneをiOS12にアップグレードしたら、iOS11で動作していたアプリが直ぐに終了する。 このとき、XCodeのターゲットのOSのバージョンを変えれば、動くのではないかと思って、ターゲットのバージョンを変えて、アプリを再構築した。 エミュレータで、動作確認をして、アプリをインストールしてから、実行してみると、直ぐに終了する。 

IPhoneを開発用マックに接続して、XCodeで実機での実行を行った。 すると、XCodeがダイアログを表示して、アプリがLaunch できない。端末(iOSデバイスの固有の名前)がアプリの実行を拒否したと表示された。

プロビジョンプロファイル

i-KeyHoleTVは、AD-HOCで開発されている。 AD-HOCは、端末の識別子(UUID)がアプリに梱包されている。 端末の識別子は、Provision Profile というファイルで、自分のAppleのアプリケーション開発ページよりダウンロードする。 このファイルを、XCodeに格納しないと、まず、アプリを実機用に作成(Achiveという表現をXCodeでは使っている)ができない。

初期のiOSの場合、端末の識別子を端末にiTunesで送る必要があったが、iOSやXCodeがバージョンアップされ、アプリに梱包された。 昔は、正しいプロビジョンプロファイルがアプリに梱包されていないと、インストールすらできなかった。おそらく、今でもできない。

iOSの脱獄というのがある。 使ったことがないが、AD-HOCのアプリケーションやアップルストアで販売されているアプリケーションがAppleStoreを介さないで、インストールできるようだ。

AppleStoreに置いているあぷりには、AppleStore用のプロビジョンプロファイルがある。このプロビジョンプロファイルがアプリに梱包されている。 脱獄は、おそらく、このプロビジョンプロファイルを識別を無効、もしくは、バイパスする処理を行っているのでないかと思っている。

動作しない原因の予想

iOS12では、iOS11以前とおそらくアプリのプロビジョンプロファイルの認識の方法が異なっているのでは、ないかと思っている。多分、脱獄や有料アプリケーションがAppleStore以外で出回るのを避ける処置がとられている。 この結果、AD-HOC用のアプリケーションが動作しなくなった。

XCode で、エミュレータを用いてデバックを行うと、正しく動作する。 しかし、実機にインストールして、動作させると、直ちに終了する。 エミュレータと実機のOSの違いは、エミュレータは、梱包されれているプロビジョンプロファイルと自分のUDIDの比較などを行わず、アプリを実行する。 このため、エミュレータは、プロビジョンプロファイルがないアプリも実行できるし、たとえプロビジョンプロファイル梱包されているアプリのUDIDの比較などの作業を行わないため、アプリが実行される。 一方、実機は、おそらく梱包されているプロビジョンプロファイルからUDIDの取り出しや自分自身のUDIDとの比較を行っているはずで、そのプログラムに不具合があるか、KeyHoleTVに梱包されているプロビジョンプロファイルの構成が異なっているため、正しく妊娠できないため、アプリが落ちると思われる。

KeyHoleTVに梱包されているプロビジョンプロファイルの構成がたとえ、おかしくなっていても、それを構築するのは、XCodeに付随するプログラムが行っている。 XCodeは、アップルが提供するソフトウェアであるため、たとえ構成が違っていても、OSが正しく処理を行う必要があると思う。

現在の対策

iOS12にアップグレードしないことが第一。もし、してしまったら、ダウングレードをする。 現在、Appleに対策を聞いている。また、iOS12のバグとして、報告も行った。 残念ながら、アプリの開発者では、対策をとる方法がみつけられない。 エミュレータで動作確認ができて、正しいプロビジョンプロファイルをXCodeにいれて、それをリリース用に仕上げても、実機でアプリが動作しないのは、おそらく、iOS12の不具合だと思う。 これを調べるためには、 iOSのデバッグが必要で、アプリの開発者では、iOSのデバックができない。 また、アプリを構成する仕様などが、明らかであれば、それに合わせることができるが、仕様は、公開されていない。 このことからも、Appleが対処しなくてはならないと思う。

 分かったこと

アプリをXCode9で再コンパイルした。 XCode10のプロジェクトをXCode9で、読込ますと、当然プロジェクトは認識できない。 仕方ないので、新しくプロジェクトを作り直した。 この時、このプロジェクトは、StoryBoard を使わないで、本当によかったと思う。 もしStroyBoardを使っていたら、全て使えない可能性が生じて、StoryBoardを一からやり直す必要がある。

さて、XCode9で、再コンパイルしたら、iOS12のデバイスで動作した。 これで、iOS12は、Code Signを調べる処理に問題があるか、XCode10がCode Signを埋め込む処理に問題があるかになった。

因みに、この問題は、AppleのBUG Reportor というバグの報告に上げている。 実は、2回同じ問題で上げているのだが、一度目は、「わざと落としている」というエンジニアの見解で、バグがクローズされた。 

Appleのテスターたちは、おそらくシミュレータに似た実機のデバイスでテストしていると想定される。 AppleStore用のCode Signに認可をするために、アプリの動作確認を行っているが、 おそらく、Code Signの確認をしない実機だろう。 これで、テストをすれば、Code Signの検証に誤りがあるのに、Code Signを検証しない実機で、テストしても現象が現れるはずもない。 だから、「わざとアプリを終了させている」という回答は、理解できる。

で、Appleは、市販されている実機で、アプリやOSの検証を行っていない可能性がある。 開発者には、実機での検証を求めているくせに、自分たちはしていない。 米国が得意の二律背反であろうと思う。

この不具合は、一でも市販の実機でiOS12のリリース時、もしくはXCode10のリリース時で試していたら、簡単に見つかる。 その手順を起こったいるとしか思えない。 おそらく、XCode10で開発した企業向けのアプリも影響がでるのでは、ないかと想定する。

更に分かったこと

XCode9を使えるようにして、ゴミ箱に入っていたXCode10を戻した。この結果、XCode10でも

iOS12で動作するipaを作ることが出来た。 何故なのかがよく分からないが、 ipa ファイルの大きさを調べると、XCode9, XCode10の併用後で、構築したipaファイルの方が大きい。 

  • iOS12で動かないipa : 873,845 バイト
  • iOS12で動く ipa         : 875,190 バイト

現在は、iOS12でも動作するアプリを OISEYER Inc. に載せている。 おもしろいことに、iOS12で動作(起動しない)アプリでも、シミュレータ、iOS10,iOS11では起動する。 このことから、何らかの不具合が、 iOS12もしくは、XCode10にあるとしか思えない。

 

続 更に分かったこと

XCode10をしばらく使っていたら、XCode10.1にインストールせよと表示され、勝手にXCodeが停止した。 しかたがないので、 XCode10.1 にアップグレードした。 その結果、 iOS12で起動しなくなった。 XCodeを消して、 ~/Library にあるXCode関連のファイルもフォルダも全て消しても、 XCode9 , XCode10.1 を再インストールしても、 iOS12.1 で起動できるアプリが作れなくなった。 しかし、 iOS10, iOS11では、アプリが起動できる。

色々調べてみたら、

stackoverflow.com

XCode10 beta でも同様の問題があって、 Key Chain アクセスに入っているApple World Wide Developer Relations Certification Authority を消せばよいらしい。

早速試したみたら、 iOS12.1 でアプリの起動が確認できた。 これで、解決と思って、AD-HOC版をリリースして、  OISEYER Inc. 上げたみた。 残念ながら、ネットでのインストールは出来なかった。 灰色のアイコンが表示されるだけ。

以上のことで、分かったこと

  • Xcodeは、Code Signをアプリに挿入している
  • 挿入場所は、 Key Chain アクセスの項目に依存する
  • iOS10, iOS11 と iOS12では、 アプリのCode Sign をアクセスする物理的な場所が異なっている。
  • ネットインストーラも、 アプリの Code Sign をアクセスしている。 しかし、参照する場所は、iOSとは異なっている。
  • おそらく、 Xcode9 では、複数の場所にCode Sign をアプリに格納している。 このため、サイズが大きくなる。

で、個人的な見解として、 iOS12 iOS12.1 は、不具合がある としか、思えない。 Appleは、少なくとも、製品テストを十分に行っていない。 自分たちが用意した Code Sign の機構で、不具合が生じている。

 

ネットで調べた結果で、 アカウントを増やす対策は、 XCode10.1 では、iOS12で起動するアプリが作れなかった。

KeyChainという史上最低なプログラム

KeyChainというプログラムがある。 このプログラムは、Mac OSに付属していて、パスワードや、Certificate、秘密鍵、公開鍵を管理するソフトウェア。 Xcodeで、iOSのアプリを作るとき、このソフトウェアを利用しないと、アプリの構築ができない。 更に、一年に一度、Appleが発行するCertificate を更新しないと、 iOSのアプリの更新ができないので、KeyChainを必ず使う必要がある。

さて、KeyChainは、内部データを利用して、鍵やCertificate を管理している。 この内部データは、Certificate の更新などにより、比較的簡単に壊れる。 壊れても、 KeyChainを使っている側からすると、壊れている認識ができないし、 表示される鍵やCertificate は、正しく格納されているように見えるし、ほとんどのMacの操作は、問題なく行える。

ところがである。 このデータが壊れると、 iOS用のアプリが突然作れなくなる。 アプリ自身は、Xcodeで作ることができるが、 動かすことができなくなる。 特に iOS12に対しては、全く動作しなくなる。 更にやっかいなことに、 壊れた内部データがないと、不具合を他の機器で

再現できないし、 壊れた内部データを吐き出す機能もない。

まとめると、KeyChainは、 内部データを簡単に壊すし、壊したことがほとんど分からない。 しかも、 壊れた内部データを Exportする機構もない。 しかし、内部データが壊れたら、他のソフトウェアに多大な迷惑をかけるが、 直接使っている人に迷惑をかけるのでなく、 生み出されたソフトウェアを利用している人に迷惑をかける。 SONYの SONYタイマーよりたちが悪いと思う。 不具合を検証させない仕組みとしては、ある意味完璧だと言える。

遅々として進まない Appleのバグ修正

Appleの Bug Reporter に、 Over the air (iOSデバイスのサファリでアプリをインストールする機能)で、 iOS12ではインストールできない不具合を上げている。 Appleから度々、このようにしてみくれ、結果を送れとの連絡が入る。 その都度、言われたことをやって、報告をしている。

このやりとりの中で、 Appleの技術者の質が落ちたと感じている。 最も質が落ちたの感じたのは、 iOSのログについてだ。 アプリが不正終了したりすると、ログがiOSデバイスの中に残る。 このログを送れとの連絡がきた。 以前から知っているが、 サファリでインストールできない不具合は、 ログが一切残らない。 同様に Code Sign が違っていても、ログが残らない。 これは、 iOSデバイスで、 Code Sign に関連した情報を外に漏らさないために Appleがわざと行っている。 Code Sign の不具合である旨を何度も伝えているにも拘らずである。 で、しかたがないので、ログをスクロールしながら、画面コピーして(画面コピーでは、画面いっぱいに表示したものしか、撮れない)で、送付した。 すると、 Appleから、 ログが送られていないとの連絡が来た。 ここで、こいつは、全然分かっていないと感じた。 そこで、ログの画面コピーの絵を一から説明して、 ログが残るぐらいなら、こちらで対処できる旨を伝えた。 すると、何も言わなくなった。 つまり、 Appleは、自分で作ったバグを解決できない。 もう少し待って、解決策がみつからない場合、 Code Signを埋め込む仕様の提出を求めようと思う。

Apple やっとバグ修正(2019年5月1日PST)

MacOSのアップデートで、10.14.4 に上げた。 上げたら、 XCodeのアップデートがあったので、アップデートした XCodeは、10.2.1 になった。 このバージョンで、AD-HOCアプリを作り、

ネットワーク上にアップロードした。 このバージョンで、iOSデバイス上でネットを介してインストールできたことを確認できた。 報告してから、約8ヵ月もかかった。 

 

なお、KeyHoleTVのダウンロード、プレミアムモジュールキーの販売は、

www.oiseyer.com

で。 

利用者からの質問と回答(その2)

f:id:KeyHoleTV:20180920072432p:plain

利用者から、KeyHoleTVが停止するとの質問を受ける。 KeyHoleTVは、UDP/IPで通信を行っているので、利用者の環境によっては、パケットが欠落する場合がある。 以前から、このような質問が届いており、その解決方法を探るため、利用者には、負担であったが、通信のテストをしてもらった。

Windows、MacやLinuxには、通信を測定できるコマンドがある。Windowsでは、コマンドプロンプトを起動する。 コマンドプロンプトは、 スタートメニュー>全てのプログラムー>アクセサリにある。 Macでは、ターミナルを起動する。ターミナルは、アプリケーションー>ユーティリティにある。 Linuxでは、端末を起動する。

コマンドプロンプト、ターミナル、端末は、コマンドを入力して、エンターキーもしくはリターンキーをヒットすると、入力したコマンドを実行する。 通信を測定できるコマンドは、 ping で、WindowsとMac/Linuxと引数の形式が異なるが、通信状態を調べることができる。

ping コマンドは、引数に対象のサーバ指定する。 

  • www.sinet.ad.jp上記にサイトには、以下のサーバが掲載されている。
  • ping-hokkaido.sinet.ad.jp
  • ping-iwate.sinet.ad.jp
  • ping-tokyo.sinet.ad.jp
  • ping-toyama.sinet.ad.jp
  • ping-mie.sinet.ad.jp
  • ping-osaka.sinet.ad.jp
  • ping-yamaguchi.sinet.ad.jp
  • ping-kochi.sinet.ad.jp
  • ping-oita.sinet.ad.jp
  • ping-okinawa.sinet.ad.jp

これらの、サーバに対してping を行えば、日本との通信速度が分かる。 往復の通信速度を30回計測するのであれば、 Windows では -n 30 とし、MacやLinux では、-c 30 とする。

ping コマンドの使い方は、以下に詳しい

www.atmarkit.co.jp

開発者のPCからのLinux でのping の結果

$ ping -c 30 ping-tokyo.sinet.ad.jp
PING ping-tokyo.sinet.ad.jp (150.100.208.3) 56(84) bytes of data.
64 bytes from 150.100.208.3: icmp_seq=1 ttl=46 time=115 ms
64 bytes from 150.100.208.3: icmp_seq=2 ttl=46 time=116 ms
64 bytes from 150.100.208.3: icmp_seq=3 ttl=46 time=115 ms
...
--- ping-tokyo.sinet.ad.jp ping statistics ---
30 packets transmitted, 30 received, 0% packet loss, time 29032ms
rtt min/avg/max/mdev = 114.793/115.637/118.426/0.750 ms

多くの利用者からの結果では、パケットロスがあり、応答時間がばらばらになるとのこと。

なんらかの通信が利用者の環境から発信・受信されており、インターネットの通信を逼迫していると分かる。 それで、利用者にネットワーク環境を教えてもらうと、WiFiを利用しているとのこと。 おそらく、WiFI経由でなんらかの通信を行っていると考えられるので、ルータもしくは、ADSL、ケーブルまたは光モデムにMACアドレスフィルターの設置をお願いする。 すると、ほとんど利用者がKeyHoleTVの視聴に問題がなくなる。

 

なお、KeyHoleTVのダウンロード、プレミアムモジュールキーの販売は、

www.oiseyer.com

で。 

YouTUBEに検証動画をあげた(地デジの放送が、KeyHoleTVより遅いのは、どうしてか)


地デジとKeyHoleTVの速度の比較

 

地デジの放送は、東京が主で放送された内容が、地方の中継局から流れる時、一旦デコードしてから、再びエンコードをするみたい。 その結果、0.5秒の遅延しかないKeyHoleTVの方が地デジより早くなる。

中継するたび、エンコード・デコードを行うと、複数の中継があれば、その分更に遅くなる可能性が高い。

 

もっとも、ワンセグでは、KeyHoleTVの方が、断然早い。


ワンセグとKeyHoleTVの受信速度の比較

 

2020年にオリンピックが東京で開かれる。当然多くの外国人が訪れるはず。 彼らの携帯電話に、緊急速報は、流れるのか。 KeyHoleTVであれば、アンドロイド端末であれば、誰でもインストールできて視聴できる。

そろそろ、日本だけの仕様というのも止めた方が良いのではないかと考える。

 

なお、KeyHoleTVのダウンロード、プレミアムモジュールキーの販売は、

www.oiseyer.com

で。

KeyHoleTV 開発者への質問と回答(その1)

利用者から、質問メールがきた。 Linux 上でのKeyHoleTVがCPU率100%になるとのこと。 こちらの開発環境 Ubuntu 14.04 と CentOS 7 で実測したところ、CPU使用率は、10%から20%。 利用者の環境は、Fredra であるそうな。

Ubutnu での実測結果 この時は、CPU使用率は10%

f:id:KeyHoleTV:20180920054343p:plain

CentOS7での実測結果 この時は、CPU使用率は、6.7%

f:id:KeyHoleTV:20180920054316p:plain

 

CPU使用率が100%になる現象は、過去Ubuntu でもあった。原因は、usleepだった。この時は、Ubuntuのシステムコールの実装で、usleep がCPU割り込みを利用しないで、ループカウンタで、タイミングを取っていたため、CPUが休まるはずもなく、100%になっていた。 この時の解決方法は、select システムコールので、標準入力をfd_set して、タイムアウトを入れて、解決した。

しかし、その後、Ubuntu がアップデートされ、POSIXに準じたシステムコールに変更され、KeyHoleTVでは、nanosleep システムコールで対応した。Thread 中でCPUを休眠させるには、nanosleep を使うので、それに対応した。

しかし、Fredraでは、nanosleep がおそらくループカウンタで実装されているのであろう。どうしたものかと考え中。

なお、KeyHoleTVのダウンロード、プレミアムモジュールキーの販売は、

www.oiseyer.com

で。